Re: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-21 Thread Jochem Maas

Michael Sims wrote:

Jochem Maas wrote:


Michael Sims wrote:


So, as far as foo() knows:

foo($a = 5);
and
foo(5);

are exactly the same...


I don't think they are, and you're examples don't prove it.
Anyone care to come up with the proof. 



No, I was wrong, Rasmus corrected me.  That's my one allowed mistake for the day.  


well if you're going to get corrected it might as well be by the man himself ;-)


I promise to wait until tomorrow before making another one. ;)


and tomorrow it is, what red herring do you have fgor us today? :-)





--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



Re: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Jasper Bryant-Greene

Lester Caine wrote:
This type of code is used in a few places, so I'd like a little help 
converting it to 'good code' under the new rules ;)


They're not new rules. PHP is just warning you where it didn't before. 
It was still bad coding practice before.




Get the key from an array ( fails because key(array) )

if( $pId == key( $this-getFunc() ) ) {

In getFunc()

return ( $this-getAssoc(select Id, Content from database...);

Current fix is just to create the array and use that
$keyarray = $this-getFunc();
if( $pGroupId == key( $keyarray ) ) {

This works fine, but is there a 'proper' way to do it now that what 
looked tidy originally fails with an error?


That is the 'proper' way, since you are using key() exactly as it is 
intended to be used, although you could avoid the reference like this:


$keys = array_keys( $this-getFunc() );
if( $pGroupId = $keys[0] ) {

--
Jasper Bryant-Greene
Freelance web developer
http://jasper.bryant-greene.name/

--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



Re: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Lester Caine

Jasper Bryant-Greene wrote:


Lester Caine wrote:

This type of code is used in a few places, so I'd like a little help 
converting it to 'good code' under the new rules ;)


They're not new rules. PHP is just warning you where it didn't before. 
It was still bad coding practice before.


Since it is not my own code ...
The problem is that little problems like this HAVE been duplicated and 
no one has complained before ;)

Now we have to go through every library and eliminate them ...


Get the key from an array ( fails because key(array) )

if( $pId == key( $this-getFunc() ) ) {

In getFunc()

return ( $this-getAssoc(select Id, Content from database...);

Current fix is just to create the array and use that
$keyarray = $this-getFunc();
if( $pGroupId == key( $keyarray ) ) {

This works fine, but is there a 'proper' way to do it now that what 
looked tidy originally fails with an error?


That is the 'proper' way, since you are using key() exactly as it is 
intended to be used, although you could avoid the reference like this:


$keys = array_keys( $this-getFunc() );
if( $pGroupId = $keys[0] ) {


Actually the proper way would be to get each function to produce a 
single result - but I'm not going to re-code everything :)


I suppose the REAL questions was - Why was using the function in this 
way a 'bad practice', is there any way that it could be made a 'good 
practice' since the intent is so obvious?
I understand the new checks, but I don't see that the original was 
particularly 'bad' - only that under some conditions it might cause a 
problem?


--
Lester Caine
-
L.S.Caine Electronic Services

--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



Re: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Jasper Bryant-Greene

Lester Caine wrote:
I suppose the REAL questions was - Why was using the function in this 
way a 'bad practice', is there any way that it could be made a 'good 
practice' since the intent is so obvious?
I understand the new checks, but I don't see that the original was 
particularly 'bad' - only that under some conditions it might cause a 
problem?




Basically, in PHP, a reference (such as what key() takes as a parameter 
[1]) can only point to an actual variable, not directly to the result of 
a function. So you have to assign the output of the function to a 
variable first.


From the PHP manual [2]:
| the following examples of passing by reference are invalid:
|
| foo(bar()); // Produces fatal error since PHP 5.1.0
| foo($a = 5); // Expression, not variable
| foo(5); // Produces fatal error

Whether this is the optimal behaviour has been the subject of recent 
debate on this list [3]. Rasmus states that the current behaviour of 
throwing a fatal error will be changed to a notice.


[1] http://php.net/key
[2] http://php.net/language.references.pass
[3] http://marc.theaimsgroup.com/?l=php-generalm=112689425109173w=2
--
Jasper Bryant-Greene
Freelance web developer
http://jasper.bryant-greene.name/

--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



Re: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Jochem Maas

Jasper Bryant-Greene wrote:

Lester Caine wrote:

I suppose the REAL questions was - Why was using the function in this 
way a 'bad practice', is there any way that it could be made a 'good 
practice' since the intent is so obvious?
I understand the new checks, but I don't see that the original was 
particularly 'bad' - only that under some conditions it might cause a 
problem?




Basically, in PHP, a reference (such as what key() takes as a parameter 
[1]) can only point to an actual variable, not directly to the result of 
a function. So you have to assign the output of the function to a 
variable first.


 From the PHP manual [2]:
| the following examples of passing by reference are invalid:
|
| foo(bar()); // Produces fatal error since PHP 5.1.0
| foo($a = 5); // Expression, not variable


wtf, Im now officially confused (before I suffered unofficially :-)

if foo() expects one args by reference then why is doing:

foo($a = 5);

..wrong? I always thought that the expression (in this form) 'returns'
the variable? or does it need to be:?

foo( ($a = 5) );

in fact I'm pretty sure that an example (like this) of a fix for
the 'bad coding' practice that is now throwing notices/errors was
given on internals-php quite recently.

I can understand that the following are wrong:

foo(5); // not sure this is wrong.
foo(bar());

but how is:

foo(($a = 5));

different from?:

$a = 5; foo($a);



| foo(5); // Produces fatal error

Whether this is the optimal behaviour has been the subject of recent 
debate on this list [3]. Rasmus states that the current behaviour of 
throwing a fatal error will be changed to a notice.


[1] http://php.net/key
[2] http://php.net/language.references.pass
[3] http://marc.theaimsgroup.com/?l=php-generalm=112689425109173w=2


--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



Re: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Jasper Bryant-Greene

Jochem Maas wrote:

Jasper Bryant-Greene wrote:

 From the PHP manual [2]:
| the following examples of passing by reference are invalid:
|
| foo(bar()); // Produces fatal error since PHP 5.1.0
| foo($a = 5); // Expression, not variable


if foo() expects one args by reference then why is doing:

foo($a = 5);

..wrong? I always thought that the expression (in this form) 'returns'
the variable? or does it need to be:?


Yes, but how can you modify $a = 5 from within foo()? It's an 
expression, not something that can be modified. This one is, admittedly, 
kinda shaky.



I can understand that the following are wrong:

foo(5); // not sure this is wrong.


This is definitely wrong. For example:

?php
function foo($a) {
$a = 6;
}

foo(5);
?

Is obviously impossible, as it tries to assign the value 6 to the 
constant value 5.


--
Jasper Bryant-Greene
Freelance web developer
http://jasper.bryant-greene.name/

--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



Re: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Jochem Maas

Jasper Bryant-Greene wrote:

Jochem Maas wrote:


Jasper Bryant-Greene wrote:


 From the PHP manual [2]:
| the following examples of passing by reference are invalid:
|
| foo(bar()); // Produces fatal error since PHP 5.1.0
| foo($a = 5); // Expression, not variable



if foo() expects one args by reference then why is doing:

foo($a = 5);

..wrong? I always thought that the expression (in this form) 'returns'
the variable? or does it need to be:?



Yes, but how can you modify $a = 5 from within foo()? It's an 
expression, not something that can be modified. This one is, admittedly, 


by definition the expression is evaluated _before_ the function is
called - so the expression is not passed to the function, the result
of the expression is passed ... I was under the impression that the the
expression evaluates to a 'pointer' (I'm sure thats bad terminology) to
$a ... which can taken by reference by the function.

possibly I am completely misunderstanding what goes on here.


kinda shaky.


I can understand that the following are wrong:

foo(5); // not sure this is wrong.



This is definitely wrong. For example:


your example make it clear, thanks!



?php
function foo($a) {
$a = 6;
}

foo(5);
?

Is obviously impossible, as it tries to assign the value 6 to the 
constant value 5.




--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



RE: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Michael Sims
Jochem Maas wrote:
 foo($a = 5);
 
 by definition the expression is evaluated _before_ the function is
 called - so the expression is not passed to the function, the result
 of the expression is passed ... I was under the impression that the
 the expression evaluates to a 'pointer' (I'm sure thats bad
 terminology) to $a ... which can taken by reference by the function.
 
 possibly I am completely misunderstanding what goes on here.

When used as an expression, an assignment evaluates to whatever is on the right 
side of the assignment operator, not the left.  Example:

var_dump($a = 5);
outputs
int(5)

var_dump($a = some string);
outputs
string(11) some string

So, as far as foo() knows:

foo($a = 5);
and
foo(5);

are exactly the same...

--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



Re: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Dragan Stanojevic - Nevidljivi

Jochem Maas wrote:
Basically, in PHP, a reference (such as what key() takes as a 
parameter [1]) can only point to an actual variable, not directly to 
the result of a function. So you have to assign the output of the 
function to a variable first.

wtf, Im now officially confused (before I suffered unofficially :-)

if foo() expects one args by reference then why is doing:

foo($a = 5);

..wrong? I always thought that the expression (in this form) 'returns'
the variable? or does it need to be:?

foo( ($a = 5) );


Well think like this: expression != variable != value :]

Let me explain... most functions (and expressions!) return value, not
variable (unless it's passed by reference). Usually, although most
beginners don't know it, you ignore that value.

For example, you could do:

fopen( $filename, $filemode );

and in that case return value (not variable) of fopen is ignored. This
is a bad practice because you need to check it, but this is just an
example. Most other functions return values that we ignore.

Another example (not functions but expressions) is assigning a value:

$a = 5; // returns 5 (and we ignore it again)

it allows us to do the following:

$a = $b = $c = 10;

read from right to left, and it'll go something like this: assign 10 to
$c (it evaluates to 10), assign (previously assigned value) 10 to $b,
and so on

So in essence: $c = 5 in expression and returns the value of 5 not a
variable/reference which can be changed.

Hope this will help you a little,
N::

P.S. Just a thought... If you declare the method to return a ref maybe
you can get away with it...

private public  getThis() {
$tempArr = array( 'a', 'b', 'c' );

return $tempArr;
}

as opposed to:

private public getThis() { ... }


smime.p7s
Description: S/MIME Cryptographic Signature


Re: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Jochem Maas

thanks everyone for the crash course in better understanding the underlying 
mechanisms!
... I'm probably not the only one that learnt something from this ;-)

Dragan Stanojevic - Nevidljivi wrote:

Jochem Maas wrote:

Basically, in PHP, a reference (such as what key() takes as a 
parameter [1]) can only point to an actual variable, not directly to 
the result of a function. So you have to assign the output of the 
function to a variable first.


wtf, Im now officially confused (before I suffered unofficially :-)

if foo() expects one args by reference then why is doing:

foo($a = 5);

..wrong? I always thought that the expression (in this form) 'returns'
the variable? or does it need to be:?

foo( ($a = 5) );



Well think like this: expression != variable != value :]

Let me explain... most functions (and expressions!) return value, not 
variable (unless it's passed by reference). Usually, although most 
beginners don't know it, you ignore that value.


For example, you could do:

fopen( $filename, $filemode );

and in that case return value (not variable) of fopen is ignored. This 
is a bad practice because you need to check it, but this is just an 
example. Most other functions return values that we ignore.


Another example (not functions but expressions) is assigning a value:

$a = 5; // returns 5 (and we ignore it again)

it allows us to do the following:

$a = $b = $c = 10;

read from right to left, and it'll go something like this: assign 10 to 
$c (it evaluates to 10), assign (previously assigned value) 10 to $b, 
and so on


So in essence: $c = 5 in expression and returns the value of 5 not a 
variable/reference which can be changed.


Hope this will help you a little,
N::

P.S. Just a thought... If you declare the method to return a ref maybe 
you can get away with it...


private public  getThis() {
$tempArr = array( 'a', 'b', 'c' );

return $tempArr;
}

as opposed to:

private public getThis() { ... }


--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



Re: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Rasmus Lerdorf
Lester Caine wrote:
 This type of code is used in a few places, so I'd like a little help
 converting it to 'good code' under the new rules ;)
 
 Get the key from an array ( fails because key(array) )
 
 if( $pId == key( $this-getFunc() ) ) {
 
 In getFunc()
 
 return ( $this-getAssoc(select Id, Content from database...);
 
 Current fix is just to create the array and use that
 $keyarray = $this-getFunc();
 if( $pGroupId == key( $keyarray ) ) {
 
 This works fine, but is there a 'proper' way to do it now that what
 looked tidy originally fails with an error?

There is nothing wrong with that code.  key() and current() don't need
to take a reference and this has been fixed in CVS and will be in the
next release.  It was overlooked in the past because we didn't have any
sort of warning about discarded references.  We have also fixed things
such that discarded references in other circumstances such as:
array_pop, array_shift, end(), etc. will only throw an E_STRICT in PHP
5.x.  E_STRICT is the new super-pendantic warning level that is disabled
by default but can be turned on to help you track down potential sources
of errors such as doing:

  sort($this-getArray());

If you have forgotten to make the getArray() method return its array by
reference, then that sort call will do absolutely nothing and it can
often be really hard to find a bug like that.

-Rasmus

-- 
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



Re: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Rasmus Lerdorf
Michael Sims wrote:
 Jochem Maas wrote:
 
foo($a = 5);

by definition the expression is evaluated _before_ the function is
called - so the expression is not passed to the function, the result
of the expression is passed ... I was under the impression that the
the expression evaluates to a 'pointer' (I'm sure thats bad
terminology) to $a ... which can taken by reference by the function.

possibly I am completely misunderstanding what goes on here.
 
 
 When used as an expression, an assignment evaluates to whatever is on the 
 right side of the assignment operator, not the left.  Example:
 
 var_dump($a = 5);
 outputs
 int(5)
 
 var_dump($a = some string);
 outputs
 string(11) some string
 
 So, as far as foo() knows:
 
 foo($a = 5);
 and
 foo(5);
 
 are exactly the same...

The value passed is the same, but when passed as $a=5 then the value has
a symbol table entry associated with it whereas if you just pass in 5 it
doesn't.  That means that:

function foo($arg) { $arg =6; }

will work if you call: foo($a=5);
but you will get an error if you have: foo(5);

The above should be pretty straightforward and isn't new.  What was
always fuzzy was this slightly more involved example:

function foo($arg) { $arg =6; }
function bar() { return 5; }
foo(bar());

Here we are essentially passing 5 to foo() again, but it isn't a
constant, it is what is known as a temp_var internally in PHP.  Chances
are code like this is hiding a bug, because the temp_var is going to
drop out of scope and the change to it in foo() will be discarded.  This
was initially made to throw a fatal error in PHP 5.x, which was a
mistake on our part.  It now throws an E_STRICT instead because in some
cases this may not actually be a bug.  There are some cases where you
don't care about the discarded reference.  In PHP 4.3.x assigning
references to temp_vars could cause memory corruption which prompted the
fixes to 4.4 and the introduction of an E_NOTICE in certain cases.

-Rasmus

-- 
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



RE: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Michael Sims
Rasmus Lerdorf wrote:
 Michael Sims wrote:
 When used as an expression, an assignment evaluates to whatever is
 on the right side of the assignment operator, not the left. 
 Example:  
[...]
 foo($a = 5);
 and
 foo(5);
 
 are exactly the same...
 
 The value passed is the same, but when passed as $a=5 then the value
 has a symbol table entry associated with it whereas if you just pass
 in 5 it doesn't.  That means that:
 
 function foo($arg) { $arg =6; }
 
 will work if you call: foo($a=5);
 but you will get an error if you have: foo(5);

Oops, sorry for posting misinformation, I was not aware of the above...  Thanks 
for the info.

--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



Re: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Jochem Maas

Michael Sims wrote:

Jochem Maas wrote:


foo($a = 5);


by definition the expression is evaluated _before_ the function is
called - so the expression is not passed to the function, the result
of the expression is passed ... I was under the impression that the
the expression evaluates to a 'pointer' (I'm sure thats bad
terminology) to $a ... which can taken by reference by the function.

possibly I am completely misunderstanding what goes on here.



When used as an expression, an assignment evaluates to whatever is on the right 
side of the assignment operator, not the left.  Example:


right so $a evaluates to 5 and a reference to the value of $a is passed. what 
you say doesn't make sense (to me)
take a look at the following:


?

$b = 6;
$c = another string;
var_dump(($a = 5), $a, ($a = some string), $a, ($a = $b), ($a = $c), $b, $c); 
  

?

as you see dumping the expression ($a = 5) and dumpimg plain old $a result in 
the same (as far as the output
is concerned) its therefore not possible to conclude that



var_dump($a = 5);
outputs
int(5)

var_dump($a = some string);
outputs
string(11) some string

So, as far as foo() knows:

foo($a = 5);
and
foo(5);

are exactly the same...


I don't think they are, and you're examples don't prove it.
Anyone care to come up with the proof. or explain to thick-eared old me
where I am mistaken.





--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



RE: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Michael Sims
Jochem Maas wrote:
 Michael Sims wrote:
 So, as far as foo() knows:
 
 foo($a = 5);
 and
 foo(5);
 
 are exactly the same...
 
 I don't think they are, and you're examples don't prove it.
 Anyone care to come up with the proof. 

No, I was wrong, Rasmus corrected me.  That's my one allowed mistake for the 
day.  I promise to wait until tomorrow before making another one. ;)

--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php




RE: [PHP] Tidying code for PHP5.0.5/PHP4.4.0

2005-09-20 Thread Murray @ PlanetThoughtful
 Jochem Maas wrote:
  Michael Sims wrote:
  So, as far as foo() knows:
 
  foo($a = 5);
  and
  foo(5);
 
  are exactly the same...
 
  I don't think they are, and you're examples don't prove it.
  Anyone care to come up with the proof.
 
 No, I was wrong, Rasmus corrected me.  That's my one allowed mistake for
 the day.  I promise to wait until tomorrow before making another one. ;)

Who was it that said, If you find that you only made one mistake today, you
weren't looking hard enough?

Oh, that's right, it was me. ;)

Off to make more mistakes...

Much warmth,

Murray
---
Lost in thought...
http://www.planetthoughtful.org

-- 
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php