ID:2208162
 
Code:
var/mob/mob = M


Problem description: I'm reading through the blue-book but occasionally I will take some code from the resource. I found a code for admin-verbs and I found this odd little bit of code. An image of the full code should be below. Could somebody explain to me what the extra /mob is for?


The variable M is defined with the type "atom":
GM_eradicate(atom/M // ...

All variables can be defined with a type, and that type determines what that variables and procs that the variable has access to.

In order to access the "key" variable of the chosen atom M, the variable must be typecasted into one of a type of object that has a key variable defined. Not all atoms have a "key" variable, so trying to access it would result in a compiler error.

If you typecast an object of a certain type as a variable of a different type, then you can get a runtime error by trying to access a variable or proc that the actual object doesn't have.

The safer way to typecast involves calling istype() before actually making the new variable that refers to it:
if(istype(M, /mob))
var mob/mob = M
// ...

This way, you don't have an unsafe variable in the rest of the code.
In response to Kaiochao
It's not the variable "M" that I don't understand. it's why it's mob/mob. Unless that -was- what you were explaining and it went right over my head. In which case I will be carefully re-reading and comparing to the DM guide so I -can- understand.
In response to Claytonctc
Okay, let's examine that line, then.
var/mob/mob = M

It's clearly a variable declaration. The syntax for declaring a variable goes like this:
var[Type]/[Name] = [Initial Value]

where:
* [Type] can be any type, such as /mob (so the variable can access all procs/vars of the /mob type, including those inherited from its ancestors, /atom/movable, /atom, and /datum), or any other type. The starting slash can be omitted.
* [Name] can be any valid identifier. It can't start with a number, and it can only contain numbers, letters, and underscores. It doesn't have to be related to the Type.
* [Initial Value] can be any expression, such as a literal value, reading a single variable, an operation on expressions, a proc call, etc.
* (= [Initial Value]) is optional and the variable defaults to null.

We can see in this particular case that [Type] is /mob, [Name] is mob, and [Initial Value] is M. By directly substituting those arguments, we get:
var/mob/mob = M
In response to Kaiochao
Hmm. Thanks for the assist. I think this will help me. If I understand correctly..

He could not just define it as var/mob = M but instead had to define it as

var/mob/mob = M

So he basically just said all mobs = M but had to say it in this long way. Sorry to test your patience, you've been pretty thorough in your explanations and I will probably save at least part of this conversation for future reference.
In response to Claytonctc
This is a verb that lets the user select any atom in the world. That includes areas, turfs, objs, and mobs. Since we know the chosen object will at least be an atom, we can declare a variable for it (M) with that type (atom).

Next, we want to handle the case where the atom is actually a mob. Because, you know: all mobs are atoms, but not all atoms are mobs. So we check if the atom is a mob (which may not always be true), and in the case that it is, now we're safe to treat it like a mob.
if(istype(M, /mob)) // check if M is actually a mob
var/mob/mob = M // now we can treat M as a mob, through the variable "mob"


The code would do the exact same thing with a variable of a different name; the fact that it's named "mob" has nothing to do with anything. It's not saying anything about all mobs, and it's not saying anything about the mob type. It's just a new variable. This does the same thing:
if(istype(M, /mob))
var mob/M_as_a_mob = M
In response to Kaiochao
Think I get it now. Thanks for your time dude.