Global Variables vs. Local Variables

2020-03-19 10:06发布

Okay, I'm not sure I'm understanding this concept properly (I'm learning PHP). If I understand correctly: Global variables can be referenced anywhere in the same document, or in documents linked with "include." Local variables can only be referenced in the function where they are.

Okay, if I understand that correctly (which is half of the reason I'm posting, to make sure I have that right) is there really a need for local variables? I mean, if each user defined their own variables and they needed to all be saved, I can see it being useful... kind of? But, using a database for that would be much simpler I'd think. What situations would I want to use local variables in?

6条回答
混吃等死
2楼-- · 2020-03-19 10:36

Just a couple of reasons to prefer local over gobal:

Variables take up memory. If every variable is in the global scope, that takes up a lot of memory. Local variables only exist while they're in scope, so they only use memory temporarily, and then that memory is freed up again.... So better memory usage is one good argument.

If all variables are global, then function A and function B might both update a variable, but neither is aware that the other has changed it, so it can lead to situations where you don't realise a value has been changed by one function, and assume that it is still valid in another.

查看更多
Rolldiameter
3楼-- · 2020-03-19 10:37

You're question was making sense right up to the point where you asked for the need of local variables. On the whole, you should avoid global variables as much as you can.

It's not uncommon for me to write some tool/webapp and have only two or three of my own global variables, that I use to set the actual application in motion.

Consider this:

$db = new PDO($conn, $usr, $pass);
function select(array $fields, $tbl, $where = '')
{
    global $db;//use the global variable
    return $db->query('SELECT '.implode(', ', $fields).' FROM '.$tbl.' WHERE '.$where);
}

In itself, you might argue that this code will work fine all the time. It's clear what $db is, and so there's no obvious error here.
However, suppose you include a couple of other files that use the same $db var, and there's a bug in one of those files, that causes $db to be reassigned:

$db = 'I used to be a PDO instnace';
select(array('*'), 'tbl');

This will show an error that will point you to the line that reads return $db->query(); and it'll say something like "trying to call method of non-object".

Good luck debugging that! Where was $db reassigned? there's no way to know except for sifting through your code step by step.

Declaring everything Global is like leaving your wallet on the side-walk every night.

It might still be where you last left it, but chances are its state (or value) has been changed (significantly) by some other entity/entities (people or code), who might have used your wallet (or variable) as their own, blissfuly unaware you left it there for future reference. When writing classes or functions, you refer to your collegues who will use that code as the user, too. So even if they meant no harm, a global is an accident, waiting to happen.

Incidentally, the function arguments are local variables, so I'm sure you're using them already, without knowing it.

It'd be far better to define the select function as follows:

function select(PDO $connection, array $fields, $tbl = 'tbl', $where = null)
{
    $query = 'SELECT '.implode(', ', $fields).' FROM '.$tbl;
    $query .= $where !== null ? ' WHERE '.$where : '';
    return $connection->query($query);
}

In this funciton I've created a local variable to make the code more readable/maintainable. Like I said, all the arguments are local variables, too, so after this function returns, any memory that was allocated to accomodate the values they held can be freed. When you're using global variables, the Garbage Collector can't do its job, because the variables remain in scope, and might be used further down the code. The memory is only freed once the script has finished running.

Globals tell the Garbage Collector to "wait a minute" every time it tries to free memory, because the script might need the variable later on. Code full of Globals is something a horder would write.

Globals (vars in the global scope) make for messy code, as you try to avoid name conflicts, you're going to find yourself declaring vars like $i_for_looping_over_array1 = 0;

Ok that might be a bit extreme, but you'll end up pseudo-namespacing your vars anyway, so why not use proper namespaces, scopes, classes, etc.?

Using the global keyword is slow

Whenever you use the global keyword inside a function, you're effectively saying: look for a variable called $someName, which can be anywhere. Passing that same variable as an argument, is telling the function use this.

When passing an object, you're actually passing a reference to that object (ie its address), so there's no lookup required. Primitives are copied, so there's no lookup either.

Think of yourself as a bartender. Where would you rather work? Pub AllIsGlobalHere, where, on your first day, your boss said: "If a customer asks for something, the bottle could be anywhere, the cellar, the floor or the top-right cupboard", or Pub CheckTheArguments. The latter being the place where you jump right in, and when a customer asks for a beer, your boss and/or customer helpfully point out which draught you should refer to.

查看更多
我想做一个坏孩纸
4楼-- · 2020-03-19 10:45

Local variables are needed for encapsulation, which is a good practice in programming.

Global variables in fact is a bad practice, because a variable can be altered anywhere in the application, and believe me, is hard to debug why the value of a variable is not the expected if you have multiples includes with multiples includes...

If you need to use a global variable, perhaps you should consider using a singleton or pass the variable as a parameter to the functions that need it.

查看更多
淡お忘
5楼-- · 2020-03-19 10:49

What situations would I want to use local variables in?

Local variables are those that defined inside local scope (functions), these variables are only available in that scope but not outside, for example:

$foo = 'foo';
function bar(){
 $foo = 'bar';
}

echo $foo; //prints foo

for instance, you can see that same variable name can be used inside local scope without any affect.

查看更多
别忘想泡老子
6楼-- · 2020-03-19 10:51

If you use only global vars, you'll need to give a new name to every new counter, haha.

The visibility of vars is needed for encapsulation: variable can be affected only by object that you want to have access to it. For example:

class Person{
  private $_money;
  public function rob(){
    return $this->_money;
  }
}

Only object of class Person can operate his money, so, if you want them, you have to get mask and gun.

查看更多
我欲成王,谁敢阻挡
7楼-- · 2020-03-19 10:55

In programming, there are many cases where you need a variable only in an isolated context. Counters, function arguments and variables for storing interim results of calculations and such, those aren't of any interest in the whole application. Furthermore, there's the special case of recursive functions. Local variables will get their own distinct addresses for each instance of the recursive function, which is a necessity for recursion to work properly. In PHP applications, however, it's advisable to avoid using global variables wherever you can.

查看更多
登录 后发表回答