Only variable references should be returned by reference

Pagina: 1
Acties:

Onderwerpen


Acties:
  • 0 Henk 'm!

  • Hipska
  • Registratie: Mei 2008
  • Laatst online: 15-09 21:08
Met m'n php script (op 5.3.1) heb ik volgend probleem:

Ik heb een Container class met &__get (by ref. voor array's) en __set, deze werkt perfect.
Daarbovenop wou ik nu een Config class maken die op te roepen is dmv Config::get('key')
(Config extends Container)
PHP: class.Config.php
7
8
9
10
11
12
public static function get($name){
        // load configuration settings
        if(is_null(static::$instance)) static::load();
        // return the value
        return static::$instance->$name;
}
PHP: class.Container.php
11
12
13
    public function &__get($name){
        if($this->__isset($name)) return $this->$name;
    }

Als ik deze code los aanroep gaat alles perfect, maar het gaat in de mist wanneer ik de code oproep in een static context:
PHP: file.php
41
42
43
if(is_null(self::$routes)) self::$routes = Config::get('routes');

foreach( self::$routes as $controller => $pattern){
Notice: Only variable references should be returned by reference in class.Container.php on line 13

Notice: Indirect modification of overloaded property Config::$routes has no effect in class.Config.php on line 11

Notice: Only variable references should be returned by reference in class.Config.php on line 11

Warning: Invalid argument supplied for foreach() in file.php on line 43
Ik heb al wat gezocht op Google naar deze foutmeldingen en ik snap dat het te maken heeft dat hij de return waarde van Config::get in static context niet graag als reference heeft ofzo. Ook heb ik verschillende oplossingen al geprobeerd (o.a. eerst de waarden in nieuwe vars steken, enz..), maar ik kom er nog niet uit.

Alvast bedankt voor de mensen die mij wat in de goede richting kunnen duwen.

[ Voor 3% gewijzigd door Hipska op 08-05-2010 13:10 . Reden: Extra code ]


Acties:
  • 0 Henk 'm!

  • frickY
  • Registratie: Juli 2001
  • Laatst online: 09:36
Post eens de volledige code, waarbij de line-numbers nog overeenkomen met die in de foutmelding. Dus sowieso class.Container.php t/m line 13.

De foutmelding die je post suggereert dat je in een functie/method die by-reference zou moeten returnen geen variabele returned maar een constante of evaluatie. En dat kan niet.
Dit is echter niet te herleiden uit de code samples die je hebt gepost.

Zie ook
Returning References
Note: If you try to return a reference from a function with the syntax: return ($this->value); this will not work as you are attempting to return the result of an expression, and not a variable, by reference. You can only return variables by reference from a function - nothing else. Since PHP 4.4.0 in the PHP4 branch, and PHP 5.1.0 in the PHP5 branch, an E_NOTICE error is issued if the code tries to return a dynamic expression or a result of the new operator.

[ Voor 61% gewijzigd door frickY op 06-05-2010 23:59 ]


Acties:
  • 0 Henk 'm!

  • Hipska
  • Registratie: Mei 2008
  • Laatst online: 15-09 21:08
Oke, ik zal later nog die container class posten, maar het komt er ruwweg op neer:
function &__get($name){ return $this->$name; }
frickY schreef op donderdag 06 mei 2010 @ 23:55:
[...]
De foutmelding die je post suggereert dat je in een functie/method die by-reference zou moeten returnen geen variabele returned maar een constante of evaluatie. En dat kan niet.
Dit is echter niet te herleiden uit de code samples die je hebt gepost.
[...]
Zoals je wel kan zien doe ik dus "return static::$instance->$name;", maar had dit al eens vervangen door "$value = static::$instance->$name; return $value;", wat niets mocht baten.

Verder vind ik het vreemd dat het geen problemen geeft bij constructies als var_dump(Config::get('routes'));

Acties:
  • 0 Henk 'm!

  • Hipska
  • Registratie: Mei 2008
  • Laatst online: 15-09 21:08
Ziezo, topicstart heeft update gekregen met de code van Container class.

Ook heb ik ondertussen eens de __get methode aangepast dat hij eerst een variable aanmaakt en dan die returned, helaas..

Acties:
  • 0 Henk 'm!

  • Voutloos
  • Registratie: Januari 2002
  • Niet online
Je __get() returnt niet altijd en ik snap hem sowieso niet. Als $this->$name bestaat kom je uberhaupt al niet langs die magic getter, dus dat hele ding slaat als een *&$@% op een drumstel.

[ Voor 17% gewijzigd door Voutloos op 08-05-2010 14:04 ]

{signature}


Acties:
  • 0 Henk 'm!

  • Hipska
  • Registratie: Mei 2008
  • Laatst online: 15-09 21:08
Ojee, nooit gedacht dat $this->$name private/protected kan zijn, terwijl __get public is?

En in het geval van de foutmelding bestaant $this->$name wel degelijk, want moest je mijn post gelezen hebben, dan ging je zien dat het met var_dump() wel werkt!

Is er iemand die WEL mijn post gelezen heeft en mij kan vertellen waarom het in een static context deze foutmelding geeft?

Acties:
  • 0 Henk 'm!

  • frickY
  • Registratie: Juli 2001
  • Laatst online: 09:36
Hipska schreef op zaterdag 08 mei 2010 @ 15:52:
Ojee, nooit gedacht dat $this->$name private/protected kan zijn, terwijl __get public is?

En in het geval van de foutmelding bestaant $this->$name wel degelijk, want moest je mijn post gelezen hebben, dan ging je zien dat het met var_dump() wel werkt!

Is er iemand die WEL mijn post gelezen heeft en mij kan vertellen waarom het in een static context deze foutmelding geeft?
Volgens mij klopt er nog steeds weinig van de code samples.
Op lijn 13 van container wordt helemaal niet returned, dus de melding "Notice: Only variable references should be returned by reference in class.Container.php on line 13" kan daar nooit gegeven zijn.
In file.php gebruik je 'self' in een globale context, maar dat kan niet, dus daar mist nog iets.
En waar komt die $instance vandaan in Config.php:9 ?

Ik probeer je post heel grondig te lezen maar er mist gewoon weg informatie om iets met je vraag te kunnen.

Is het probleem niet dat je probeert een reference naar een protected property naar buiten de object-scope te returnen, waardoor de property feitelijk ook vanuit buiten het object aangepast kan worden, wat nou juist niet de bedoeling is van protected vars?

[ Voor 7% gewijzigd door frickY op 08-05-2010 17:02 ]


Acties:
  • 0 Henk 'm!

  • Hipska
  • Registratie: Mei 2008
  • Laatst online: 15-09 21:08
frickY schreef op zaterdag 08 mei 2010 @ 16:59:
Volgens mij klopt er nog steeds weinig van de code samples.
Op lijn 13 van container wordt helemaal niet returned, dus de melding "Notice: Only variable references should be returned by reference in class.Container.php on line 13" kan daar nooit gegeven zijn.
Geloof het of niet, maar op lijn 13 staat wel degelijk dat } en php durft wel nog eens een fout geven op een lijn waar de eigenlijke fout de lijn erboven staat.
In file.php gebruik je 'self' in een globale context, maar dat kan niet, dus daar mist nog iets.
Zoals dus al vermeld; STATIC context m.a.w. zit het dus in een static methode.
En waar komt die $instance vandaan in Config.php:9 ?
Dat is een instantie van het config object, zoals de naam wel al zou moeten vermoeden? deze is als private static $instance gedefiniëerd.
Ik probeer je post heel grondig te lezen maar er mist gewoon weg informatie om iets met je vraag te kunnen.
Heb je dan liever dat ik alle code op een pastebin plaats ofzo?
Is het probleem niet dat je probeert een reference naar een protected property naar buiten de object-scope te returnen, waardoor de property feitelijk ook vanuit buiten het object aangepast kan worden, wat nou juist niet de bedoeling is van protected vars?
Volgens mij heb je het hier wel ongeveer in de juiste richting. Ik weet niet of deze vars nou private of protected zijn, maar dan blijft nog steeds de vraag waarom het net fout gaat wanneer deze in een static context geplaatst worden, en niet bij gewoon gebruik?

Acties:
  • 0 Henk 'm!

  • frickY
  • Registratie: Juli 2001
  • Laatst online: 09:36
Hipska schreef op zaterdag 08 mei 2010 @ 18:39:
Zoals dus al vermeld; STATIC context m.a.w. zit het dus in een static methode.
Ik bedoel dat die 'self' verwijst naar de class waarbinnen die wordt gecalled. Maar omdat je alleen de filename (file.php) geeft weet ik niet of dat Config, Container of iets willekeurig anders i
Dat is een instantie van het config object, zoals de naam wel al zou moeten vermoeden? deze is als private static $instance gedefiniëerd.
Dan zijn die static-calls naar properties in Config.php dus een typo en bedoel je self
Heb je dan liever dat ik alle code op een pastebin plaats ofzo?
Nee hoor, alleen de relevante en complete code incl bijbehorende lijnnummers uit de foutmeldingen zijn voldoende ;) Het totaalplaatje blijft nu wat troebel


Voor zover ik kan herleiden is dit wat je in zijn volledigheid doet;
PHP:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
<?php
class Config {
    protected static $instance = null;

    protected $fu = 'fu';

    public function &__get($name) { 
            if(isset($this->$name)) return $this->$name; 
            else return null;
    }

    public static function get($name){ 
            // load configuration settings 
            if(is_null(self::$instance)) self::load(); 
            // return the value 
            return self::$instance->$name; 
    }

    protected static function load() {
        self::$instance = new self();
    }

}


$a = Config::get('fu');
echo '<pre>$a ';
var_dump($a);
echo '</pre>';

$b = Config::get('bar');
echo '<pre>$b ';
var_dump($b);
echo '</pre>';

?>


Nu krijg je eenmalig de foutmelding "Only variable references should be returned by reference" voor de call van "get('bar');", zonder je static-calls
Het lijkt dus iets te maken te hebben met dynamic properties. Voor 'fu' gaat het immers wel goed.

Pas trouwens op dat je het Registry-pattern niet aan het heruitvinden bent ;)

[ Voor 73% gewijzigd door frickY op 08-05-2010 22:22 ]

Pagina: 1