From 9022821bcf8a241de4a2f4ff3c8e4a6e1fff995e Mon Sep 17 00:00:00 2001 From: tianfenghan Date: Wed, 25 Mar 2026 13:20:57 +0800 Subject: [PATCH] =?UTF-8?q?refactor(Php):=20=E4=BC=98=E5=8C=96PHP=E7=BC=96?= =?UTF-8?q?=E8=AF=91=E5=99=A8=E4=B8=AD=E7=9A=84=E6=95=B0=E7=BB=84=E5=B1=95?= =?UTF-8?q?=E5=BC=80=E5=92=8C=E5=AF=B9=E8=B1=A1=E8=BD=AC=E6=8D=A2=E9=80=BB?= =?UTF-8?q?=E8=BE=91?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - 数组展开语法直接传递数组变量,避免创建不必要的临时变量 - 对象转换逻辑中添加对已存在包装器的检查和处理 - 添加php_get_object_wrap辅助函数用于对象包装处理 - 优化代码结构,减少临时变量的使用 --- src/Php/CompilerBase.php | 44 ++++++++++++++++++++++++---------------- src/cpp/php_aot_helper.h | 7 +++++++ 2 files changed, 34 insertions(+), 17 deletions(-) diff --git a/src/Php/CompilerBase.php b/src/Php/CompilerBase.php index 34b6a5ed..b7a45402 100644 --- a/src/Php/CompilerBase.php +++ b/src/Php/CompilerBase.php @@ -2464,10 +2464,16 @@ class CompilerBase extends \PhpAot\Core\Translator if ($i !== $last) { $this->fatalError($arg, 'The unpack expression for variadic arguments must be the last'); } - $tmpVar = $this->genTmpVarName(); - $this->context->beforeStmtLines[] = self::TYPE_ARRAY . ' ' . $tmpVar . '{' . implode(', ', $list_args) . '};'; - $this->context->beforeStmtLines[] = $tmpVar . '.merge(' . $this->parseArrayArg($arg) . ');'; - return $tmpVar; + // 如果第一个参数是数组变量,数组展开语法直接传递该变量,没必要创建临时变量 + // 例如:function (array $args) { var_dump(...$args); } + if ($i === 0 and $this->isVarExpr($arg->value) and $this->getVarType($arg->value->name) === self::TYPE_ARRAY) { + return $this->parseIdentifier($arg->value); + } else { + $tmpVar = $this->genTmpVarName(); + $this->context->beforeStmtLines[] = self::TYPE_ARRAY . ' ' . $tmpVar . '{' . implode(', ', $list_args) . '};'; + $this->context->beforeStmtLines[] = $tmpVar . '.merge(' . $this->parseArrayArg($arg) . ');'; + return $tmpVar; + } } $list_args[] = $this->parseArg($arg); } @@ -3566,20 +3572,24 @@ class CompilerBase extends \PhpAot\Core\Translator protected function convertToObject(NodeAbstract $object): string { $id = $this->parseIdentifier($object); - if ($this->isVarExpr($object) and $this->getVarType($id) === self::TYPE_OBJECT) { - return $id; - } - - if (isset($this->context->objectWrappers[$id])) { - return $this->context->objectWrappers[$id]; + if ($this->isVarExpr($object)) { + if ($this->getVarType($id) === self::TYPE_OBJECT) { + return $id; + } + if (isset($this->context->objectWrappers[$id])) { + return 'php_get_object_wrap(' . $this->context->objectWrappers[$id] . ', ' . $id . ')'; + } else { + $tmpVar = $this->genTmpVarName(); + $this->addLocalVar($tmpVar, self::TYPE_OBJECT); + $this->context->beforeStmtLines[] = $this->getIndent() . $tmpVar . ' = ' . $id . ';'; + $this->context->objectWrappers[$id] = $tmpVar; + return $tmpVar; + } + } else { + $tmpVar = $this->genTmpVarName(); + $this->context->beforeStmtLines[] = $this->getIndent() . self::TYPE_OBJECT . ' ' . $tmpVar . ' = ' . $id . ';'; + return $tmpVar; } - - $tmpVar = $this->genTmpVarName(); - $this->addLocalVar($tmpVar, self::TYPE_OBJECT); - $this->context->beforeStmtLines[] = $this->getIndent() . $tmpVar . ' = ' . $id . ';'; - $this->context->objectWrappers[$id] = $tmpVar; - - return $tmpVar; } protected function convertToRef(NodeAbstract $expr): string diff --git a/src/cpp/php_aot_helper.h b/src/cpp/php_aot_helper.h index eb849455..ad039bcc 100644 --- a/src/cpp/php_aot_helper.h +++ b/src/cpp/php_aot_helper.h @@ -23,3 +23,10 @@ extern void php_restore_scope(php::Scope &ori_scope); static inline auto php_get_create_object_fn(zend_class_entry *ce) { return ce->create_object ? ce->create_object : zend_objects_new; } + +static inline php::Object &php_get_object_wrap(php::Object &obj, php::Var &var) { + if (UNEXPECTED(obj.isNull())) { + obj = var; + } + return obj; +}