The error was added in PHP7 and I have problem with such code as:
(some complex expression)->my_property = 1
Please note I am assigning to the field of the object, not to the object itself (assigning to temporary object does not make sense, I agree, but here it is not the case).
This gives me an error “cannot use temporary expression in write context”. When I rewrite this as:
$tmp = (some complex expression);
$tmp->my_property = 1;
Everything is fine. The problem is I have to have single expression (assignment is an expression), and since PHP does not support comma operator now I am toasted with two statements.
For me this is huge difference, because I cannot pass entire code as an expression further. Everything is valid inside that “complex expression” so I would love to simply disable that check in PHP.
Is it possible? How?
My code is written automatically (it is generated) and the outcome of the expression is a valid PHP object, the problem is PHP somehow does not notice it. Besides, the second form works.
Update: this is an example of complex expression I mentioned above:
(($a = foo()) === 0 ? $a : bar())
I’m going to say no.
Everything is valid inside that “complex expression” so I would love to simply disable that check in PHP.
I think the issue here is that disallowing writing to temporary expressions is not simply a “check” in PHP but a part of the language as of 7.1 (introduced in 5c2120b
).
As of 5c2120b
, the language grammar has been updated to redefine what is deferenceable as:
dereferencable:
variable { $$ = $1; }
| '(' expr ')' { $$ = $2; zend_do_begin_variable_parse(TSRMLS_C); $$.EA = 0; }
| dereferencable_scalar { $$ = $1; zend_do_begin_variable_parse(TSRMLS_C); $$.EA = 0; }
;
Additionally, you’ll notice that the sources of those errors in the codebase don’t check anything before producing an error, e.g. 1 and 2.
The workaround would be to downgrade to a version of PHP that allowed this.
Answer:
I had this error come up while refactoring some badly written code:
class MyClass {
static $cache = [];
public function myFunction() {
$this->cache['foo'] = 'bar';
}
I rewrote this to fix the non-static reference to $cache
inside myFunction
:
class MyClass {
static $cache = [];
public function myFunction() {
self::cache['foo'] = 'bar';
}
Notice I missed the $
and should have written self::$cache['foo']
.
This produced the error cannot use temporary expression in write context
, which wasn’t particularly helpful. In my case there was nothing wrong with what I was trying to do, just simple typo.
Answer:
This is very simple to understand.
When you try to call Someclass::somevar, it means, that you’r trying to call “const” var from class, i.e constant variable, like “define()”, but inside class. But when yor’r calling Someclass::$somevar, you’r calling “static” var, similar to object $someclass->somevar.
This is just a very simple explanation for beginners or php-dummies.
For more understanding there is some examples http://php.net/manual/en/language.oop5.static.php
Answer:
This is an assignment error. You are running a statement like “(($a = foo()) === 0 ? $a : bar())” but the result isn’t a class instance or variable. It’s just a random piece of code that ran. That’s why your second answer works because you are assigning the statement to the class $tmp. Likewise when Henry used “self::cache[‘foo’] = ‘bar’;” that also was an assignment to a statement, not a member variable. When he made it a variable the code worked.
If you want this on one line you would either have to keep with the original class $a and do $a->my_property = 1 or go with your second option and assign the code to a class object you create ($tmp = (($a = foo()) === 0 ? $a : bar())->my_property = 1
). This code also assumes $a has a public member “my_property”.