1. php 的版本 :PHP 7.3.0-dev (cli) (built: Mar 18 2018 00:28:55) ( NTS )

2. unless

  语法结构:

  unless($cond){

    statement;

  }

  语法作用:

  当 $cond 为假的时候,执行 statement 语句。

3. 代码修改

  词法分析文件 : Zend/zend_language_scanner.l , 大约 1195 的地方,添加 5 -7 行、 13 - 15 行内容 :

  1. <ST_IN_SCRIPTING>"while" {
  2. RETURN_TOKEN(T_WHILE);
  3. }
  4.  
  5. <ST_IN_SCRIPTING>"unless" {
  6. RETURN_TOKEN(T_UNLESS);
  7. }
  8.  
  9. <ST_IN_SCRIPTING>"endwhile" {
  10. RETURN_TOKEN(T_ENDWHILE);
  11. }
  12.  
  13. <ST_IN_SCRIPTING>"endunless" {
  14. RETURN_TOKEN(T_ENDUNLESS);
  15. }

  语法分析文件 :  Zend/zend_language_parser.y , 添加内容:

  文件大约 271 行处, 添加 T_UNLESS 和 T_ENDUNLESS 内容:

  1. reserved_non_modifiers:
  2. T_INCLUDE | T_INCLUDE_ONCE | T_EVAL | T_REQUIRE | T_REQUIRE_ONCE | T_LOGICAL_OR | T_LOGICAL_XOR | T_LOGICAL_AND
  3. | T_INSTANCEOF | T_NEW | T_CLONE | T_EXIT | T_IF | T_ELSEIF | T_ELSE | T_ENDIF | T_ECHO | T_DO | T_WHILE | T_ENDWHILE
  4. | T_FOR | T_ENDFOR | T_FOREACH | T_ENDFOREACH | T_DECLARE | T_ENDDECLARE | T_AS | T_TRY | T_CATCH | T_FINALLY
  5. | T_THROW | T_USE | T_INSTEADOF | T_GLOBAL | T_VAR | T_UNSET | T_ISSET | T_EMPTY | T_CONTINUE | T_GOTO
  6. | T_FUNCTION | T_CONST | T_RETURN | T_PRINT | T_YIELD | T_LIST | T_SWITCH | T_ENDSWITCH | T_CASE | T_DEFAULT | T_BREAK
  7. | T_ARRAY | T_CALLABLE | T_EXTENDS | T_IMPLEMENTS | T_NAMESPACE | T_TRAIT | T_INTERFACE | T_CLASS
  8. | T_CLASS_C | T_TRAIT_C | T_FUNC_C | T_METHOD_C | T_LINE | T_FILE | T_DIR | T_NS_C | T_UNLESS | T_ENDUNLESS
  9. ;

  文件大约 152 行处, 添加 2 和 4 行 的内容:

  1. %token T_WHILE "while (T_WHILE)"
  2. %token T_UNLESS "unless (T_UNLESS)"
  3. %token T_ENDWHILE "endwhile (T_ENDWHILE)"
  4. %token T_ENDUNLESS "endunless (T_ENDUNLESS)"

  大约 235 行处 , 增加 unless_statement :

  1. %type <ast> expr optional_expr while_statement unless_statement for_statement foreach_variable

  大约 428 行处, 增加 3 和 4 行的内容 :

  1. | T_WHILE '(' expr ')' while_statement
  2. { $$ = zend_ast_create(ZEND_AST_WHILE, $3, $5); }
  3. | T_UNLESS '(' expr ')' unless_statement
  4. { $$ = zend_ast_create(ZEND_AST_UNLESS, $3, $5); }

   大约 598 行处 ,增加 6 - 9 行的内容 :

  1. while_statement:
  2. statement { $$ = $1; }
  3. | ':' inner_statement_list T_ENDWHILE ';' { $$ = $2; }
  4. ;
  5.  
  6. unless_statement:
  7. statement { $$ = $1; }
  8. | ':' inner_statement_list T_ENDUNLESS ';' { $$ = $2; }
  9. ;

  Zend/zend_ast.h 的头文件中 ,大约 134 行处 , 增加 2 行的内容:   

  1. ZEND_AST_GROUP_USE,
  2. ZEND_AST_UNLESS,
  3.  
  4. /* 3 child nodes */

  Zend/zend_ast.c 的文件中, 函数 zend_ast_export_stmt 内,大约 915 行处, 添加 7 行的内容:

  1. zend_ast_export_indent(str, indent);
  2. zend_ast_export_indent(str, indent);
  3. zend_ast_export_ex(str, ast, 0, indent);
  4. switch (ast->kind) {
  5. case ZEND_AST_LABEL:
  6. case ZEND_AST_IF:
  7. case ZEND_AST_UNLESS:
  8. case ZEND_AST_SWITCH:
  9. case ZEND_AST_WHILE:
  10. case ZEND_AST_TRY:
  11. case ZEND_AST_FOR:
  12. case ZEND_AST_FOREACH:
  13. case ZEND_AST_FUNC_DECL:
  14. case ZEND_AST_METHOD:
  15. case ZEND_AST_CLASS:
  16. case ZEND_AST_USE_TRAIT:
  17. case ZEND_AST_NAMESPACE:
  18. case ZEND_AST_DECLARE:
  19. break;
  20. default:
  21. smart_str_appendc(str, ';');
  22. break;
  23. }
  24. smart_str_appendc(str, '\n');

  Zend/zend_compile.c 的文件中 ,

  大约 4667 行, 添加 zend_compile_ unless 函数 :

  1. void zend_compile_unless(zend_ast *ast)
  2. {
  3. zend_ast *cond_ast = ast->child[0];
  4. zend_ast *stmt_ast = ast->child[1];
  5. znode cond_node;
  6.  
  7. uint32_t opnum_cond;
  8.  
  9. zend_compile_expr(&cond_node,cond_ast);
  10.  
  11. opnum_cond = zend_emit_cond_jump(ZEND_JMPNZ,&cond_node,0);
  12.  
  13. zend_compile_stmt(stmt_ast);
  14.  
  15. zend_update_jump_target_to_next(opnum_cond);
  16. }

  zend_compile_stmt 函数中, 大约 8200 行处 :

  1. case ZEND_AST_IF:
  2. zend_compile_if(ast);
  3. break;
  4. case ZEND_AST_UNLESS:
  5. zend_compile_unless(ast);
  6. break;

4. 删除 Zend 目录下的 zend_language_parser.c 和 zend_language_scanner.c 文件,重新编译,安装 php .

5. 测试代码:

  1. <?php
  2. unless(0)
  3. {
  4. echo "Hello the world!\n";
  5. }
  6.  
  7. unless(0):
  8. echo "Hello the world!\n";
  9. endunless;

输出:

  1. root@ubuntu:~/tmp# php a.php
  2. Hello the world!
  3. Hello the world!

参考:

http://www.laruence.com/2010/07/16/1648.html

php 加入 unless 语法的更多相关文章

  1. 我的MYSQL学习心得(一) 简单语法

    我的MYSQL学习心得(一) 简单语法 我的MYSQL学习心得(二) 数据类型宽度 我的MYSQL学习心得(三) 查看字段长度 我的MYSQL学习心得(四) 数据类型 我的MYSQL学习心得(五) 运 ...

  2. Swift与C#的基础语法比较

    背景: 这两天不小心看了一下Swift的基础语法,感觉既然看了,还是写一下笔记,留个痕迹~ 总体而言,感觉Swift是一种前后端多种语言混合的产物~~~ 做为一名.NET阵营人士,少少多多总喜欢通过对 ...

  3. 探索C#之6.0语法糖剖析

    阅读目录: 自动属性默认初始化 自动只读属性默认初始化 表达式为主体的函数 表达式为主体的属性(赋值) 静态类导入 Null条件运算符 字符串格式化 索引初始化 异常过滤器when catch和fin ...

  4. [C#] 回眸 C# 的前世今生 - 见证 C# 6.0 的新语法特性

    回眸 C# 的前世今生 - 见证 C# 6.0 的新语法特性 序 目前最新的版本是 C# 7.0,VS 的最新版本为 Visual Studio 2017 RC,两者都尚未进入正式阶段.C# 6.0 ...

  5. Velocity初探小结--velocity使用语法详解

    做java开发的朋友一般对JSP是比较熟悉的,大部分人第一次学习开发View层都是使用JSP来进行页面渲染的,我们都知道JSP是可以嵌入java代码的,在远古时代,java程序员甚至在一个jsp页面上 ...

  6. node.js学习(二)--Node.js控制台(REPL)&&Node.js的基础和语法

    1.1.2 Node.js控制台(REPL) Node.js也有自己的虚拟的运行环境:REPL. 我们可以使用它来执行任何的Node.js或者javascript代码.还可以引入模块和使用文件系统. ...

  7. C#语法糖大汇总

    首先需要声明的是"语法糖"这个词绝非贬义词,它可以给我带来方便,是一种便捷的写法,编译器会帮我们做转换:而且可以提高开发编码的效率,在性能上也不会带来损失.这让java开发人员羡慕 ...

  8. 值得注意的ibatis动态sql语法格式

    一.Ibatis常用动态sql语法,简单粗暴用一例子 <select id="iBatisSelectList" parameterClass="java.util ...

  9. Flex 布局教程:语法篇

    作者: 阮一峰 网页布局(layout)是CSS的一个重点应用. 布局的传统解决方案,基于盒状模型,依赖 display属性 + position属性 + float属性.它对于那些特殊布局非常不方便 ...

  10. postgresql 基本语法

    postgresql数据库创建/修改/删除等写入类代码语法总结: 1,创建库 2,创建/删除表 2.1 创建表 create table myTableName 2.2 如果表不存在则创建表 crea ...

随机推荐

  1. Java第二次作业第二题

    请编写图像界面程序,用户在第一文本行输入数字,有三个按钮,分别是计算2进制,8进制,16进制,点击其中一个按钮,第一个文本行中的数据转换为相应进制的数显示在第二个文本行中. package naizi ...

  2. C#基础知识总结(一)

    1.什么是匿名函数?匿名函数,就是没有名字的函数,或者说就是一组代码块,他的参数只有在方法块内有效,可以有效的减小创建方法事所需要的系统开销 2.lambda表达式是什么?lambda表达式 就是一个 ...

  3. [Leetcode][动态规划] 买卖股票的最佳时机IV

    一.题目描述 给定一个数组,它的第 i 个元素是一支给定的股票在第 i 天的价格. 设计一个算法来计算你所能获取的最大利润.你最多可以完成 k 笔交易. 注意: 你不能同时参与多笔交易(你必须在再次购 ...

  4. Linux入门基础之 下

    八.Linux 管道.重定向及文本处理 8.1.Linux 多命令协作:管道及重定向 8.1.1 开源文化 开源文化的核心理念之一就是不要重复发明轮子,很多的开源软件都是现有软件.代码.功能的重新组合 ...

  5. 【linux】linux固定ip

    vi /etc/sysconfig/network-scripts/ifcfg-ens33  ifcfg-ens33为ifconfig显示的网卡名 TYPE="Ethernet"P ...

  6. jQuery的内容选择器

    JQuery中的内容选择器 JQuery中的内容选择器有四个: :contains(text) 匹配包含给定文本的元素 :empty 匹配所有不包含子元素或者文本的空元素 :has(selector) ...

  7. Java线程池基础

    目录: 一.线程池概述 二.线程池参数 三.线程池的执行过程 四.线程池的主要实现 五.线程池的使用 六.线程池的正确关闭方式 七.线程池参数调优 一.线程池概述 1.线程池类 目前线程池类一般有两个 ...

  8. 小红书第五章——引用类型之function类型

    有趣的函数——function类型 函数实际上是对象,每个函数都是function类型的实例,具有属性和方法. 1.函数的定义方法 1)函数声明语法 function sum(num1,num2){/ ...

  9. Scrapy项目 - 实现腾讯网站社会招聘信息爬取的爬虫设计

    通过使Scrapy框架,进行数据挖掘和对web站点页面提取结构化数据,掌握如何使用Twisted异步网络框架来处理网络通讯的问题,可以加快我们的下载速度,也可深入接触各种中间件接口,灵活的完成各种需求 ...

  10. 1.html基础知识

    1.html定义: html是一种超文本标记语言,“超文本”是指页面可以包含图片.链接.音乐.程序等非文字元素. Html不是一种编程语言. 2.html5的新特性: 用于绘画的canvas元素: 用 ...