新语言使用nl来作为临时名称(new language的首字母缩写),语法和特性基于Lua,正在实现中。

nl语法和特性完全基于Lua的语法,保证默认情况下兼容Lua代码。修改的地方罗列如下:

新增空白符将作为另外的字符串连接符,将任意类型的两个变量写在一起表示将其作为字符串连接,即

a b
// 等同于
tostring(a) .. tostring(b)
// 所以:
"a" "b" => "ab"
"a" "1" => "a1"
"a" 1 => "a1"
1 2 => "12"

空白连接符优先级高于Lua的字符串连接符..,并且高于算术运算符。Lua的字符串连接符的优先级是低于算术运算符的。

字符串在进行算术运算时自动转换成数字(无法转换的被转换为0)

"1" + 1 结果为 2
"1" + "1" 结果为 2
"1a" + 1 结果为 2
"1a" + "a1" 结果为 1
"abc" + "abc" 结果为 0

结合上述两个特性,有下面的结论:下面的Lua代码得到的是字符串"a3":

"a" .. 1 + 2

而nl中的写法和结果是(当然,上述代码在nl中执行也会得到同样的结果"a3"):

"a" 1 + 2
=>  "a1" + 2
=> 0 + 2
=> 2

下面的代码在nl中将得到(注意空格):

1 1 + 1 1
=> "1" "1" + "1" "1"
=> "11" + "11"
=> 11 + 11
=> 22

变量默认为nil,但是对nil的操作特性有变化:

nil + var // 算数运算时nil转换为0,等价于 0 + var</span>
nil var // 字符串连接操作,nil转换成空字符串,等价于 "" var</span>
nil > 1 // 等价于 0 > 1
nil [ key ] = value // 等价于 var = { key = value }
nil [k1][k2][k3] = value // 等价于 var = { k1 = { k2 = { k3 = value } } }
nil [k1][k2][k3] // 索引nil返回值为nil,故整式等价于 nil
nil () // 等价于 (def()end)()

除了1、对函数类型进行函数调用;2、对包含__call函数的table进行函数调用;对其他的值得调用均转换成调用空函数,即什么都不做,返回nil:

(def()end)() // 调用空函数

新增table计数函数table.size(),将得到全部元素的数量。

a={1,a=1}
table.size(a) // 得到的值是2

pairs函数可以接受非table类型的值,返回值是通过table.insert将此值插入空表的结果:

a = 11
for k, v in pairs(a) doprint(k, v)
end
// 打印出的东西是 1 11 ,pairs(a)相当于pairs({a})。

全部参数都有默认值,可以通过=来显式指定,不指定则认为默认值为nil。语法为:

def func( p1=1, p2, p3=3, p4 ) end
// 等价于:
def func( p1=1, p2=nil, p3=3, p4=nil ) end

函数调用时可以通过参数名传递参数,未指定名称的参数依次传递给空缺的形参。调用上述func函数的语法为:

func ( 11, p3 = nil, p4=44 )
// 相当于这么调用:
func ( p1 = 11, p2 = nil, p3 = nil, p4 = 44 )
// 即先将指定名称的实参放置到对应的形参位置处,再依次用无名称实参去填充剩余的形参。
// 最终func得到的值是:
func ( p1 = 11, p2 = nil, p3 = nil, p4 = 44 )
// 即,如果实参没有指定,则以默认值作为最终结果;如果指定,则以指定的为准。
// 上例中,p3指定为nil,虽然默认值为3,但是最终函数得到的还是nil。// 再举个例子:
func ( p1 = 11, p2 = nil, p3 = 33 )
// 最终得到的参数值是:
func ( p1 = 11, p2 = 22, p3 = nil, p4 = 4 )
// 可以看到,即使p2和p4在调用时似乎都是nil,但是最终的值的优先级为:指定的值 > 默认值。所以p2被指定的nil,p4为默认值4。

增加操作符 += -= *= /=

默认遵守lua的规则,通过启动参数可以配置一些不同的特性。

--var-define:局部变量使用空前缀来定义,全局变量使用global关键字来定义。

--func-define:function增加一个等效关键字def,如果原来的代码中def已经作为变量名,则会出现错误。

--nl:完全采用nl的新规则,适合针对nl编写的全新代码。

新增线程模块thread,用来支持多线程编程。定义如下:

thread(func) // 创建并返回一个暂停的线程
thread.suspend() // 暂停线程
thread.resume() // 恢复暂停的线程,或重启已经结束的线程
thread.valid() // 线程是否已经结束
thread.pause() // 暂停线程thread.queue.new( name ) // 创建一个所有线程均可见的队列。
thread.queue.in( channel_name, var ) // 将一个变量(数字/字符串)拷贝到通道中。userdata使用同一份,不会真的拷贝。
thread.queue.out( channel_name ) // 获取通道中最老的变量
thread.queue.die( channel_name, var ) // 将当前线程的变量(任意类型)放到通道中,自己彻底结束(die函数永远不会返回)thread.pool( size ) // 创建一个包含size个线程的暂停的线程池
thread.pool.suspend() // 暂停线程
thread.pool.resume() // 恢复暂停的线程池。没有回调函数需要被执行的情况下,该函数直接返回成功
thread.pool.valid() // 是否没有线程在运行了
thread.pool.stop() // 结束线程池
thread.pool.add( callback ) // 线程回调函数。会被执行一次。
thread.pool.remove( callback ) // 对正在运行callback函数的线程执行stop操作

为什么要做如上修改?通过下面的例子可以略窥一斑。这个函数的功能是对二维矩阵进行赋值,并且通知注册的矩阵值变化监听函数。

function assign( obj, row, col, value )if not obj then return endrow = row or 1col = col or 1value = value == nil and true or value // 支持value的值等于被赋值为falseobj.matrix = obj.matrix or {}obj.matrix[row] = obj.matrix[row] or {}obj.matrix[row][col] = valueif obj.callbacks and type(obj.callbacks) == 'table' thenfor _, callback in pairs(obj.callbacks) doif callback and type(obj.update) == 'function' then callback( value ) endendend
end

上面的Lua代码在nl中的等效实现为:

def assign( obj, row = 1, col = 1, value = true )obj.matrix[row][col] = valuefor _, callback in pairs(obj.callbacks) do callback( value ) end
end

可以看到极大的简化。

实现设想:

  1. 使用C++完成。
  2. 词法语法解析使用Flex和Bison完成。
  3. table的实现使用map实现,需要将类型抽象为一个类。
  4. 垃圾收集器使用Lua的思想实现。
  5. 算法优先文法通过修改Lua的语法定义实现。
  6. 自定义字节码和资源的内存表示方式;将源码解析为字节码和资源后,使用虚拟机执行。
  7. 虚拟机:每个变量作用域使用一个集合来存储所有可见的变量名,作用域结束时销毁集合。

基于Lua的新语言NL相关推荐

  1. R语言dplyr包使用case_when函数和mutate函数生成新的数据列实战:基于单列生成新的数据列、基于多列生成新的数据列

    R语言dplyr包使用case_when函数和mutate函数生成新的数据列实战:基于单列生成新的数据列.基于多列生成新的数据列 目录

  2. 基于Lua脚本语言的嵌入式UART通信的实现

    随着变电站智能化程度的逐步提高,对温度.湿度等现场状态参量的采集需求也越来越多.就目前而言,在现场应用中,此类设备多采用RS232或RS485等UART串行通信方式和IED(Intelligent E ...

  3. 一、ESP8266入门(基于LUA开发)

    序 一入坑便停不下来...  还挺有意思的哈,233,,,,  资料杂,自己一个一个去找确实浪费了不少时间,而且大多还都是英文的,需要硬着头皮看.  这次实践入门,更是对英语的重要确信无疑.Githu ...

  4. 《游戏AI开发指南(基于Lua的人工智能在游戏中的应用)》(Yanlz+Unity+SteamVR+5G+AI+VR云游戏+Lua+人机交互+沙箱+导航+决策树+影响力地图+立钻哥哥+==)

    <游戏AI开发指南(基于Lua的人工智能在游戏中的应用)> <游戏AI开发指南(基于Lua的人工智能在游戏中的应用)> 版本 作者 参与者 完成日期 备注 YanlzAI_Lu ...

  5. 为什么我们需要一门新语言——Go语言

    编程语言已经非常多,偏性能敏感的编译型语言有 C.C++.Java.C#.Delphi和Objective-C等,偏快速业务开发的动态解析型语言有 PHP.Python.Perl.Ruby.JavaS ...

  6. 以太坊联合创始人发明了新语言叫板Vyper,主链之后语言将引领新一轮大战?...

    作者 / Blockgeeks 编译 / Aholiab 在之前的文章中,营长从特性.规则和应用的角度,向大家全面介绍了以太坊新的合约语言Vyper的内容,很多朋友表示想看Vyper编程的实例. 在今 ...

  7. lua软件测试自动化,一种基于Lua脚本的嵌入式软件自动化测试系统及方法专利_专利查询 - 天眼查...

    1.一种基于Lua脚本的嵌入式软件自动化测试系统,其特征在于,所述系统包括:目标 测试系统及测试主控系统,其中: 目标测试系统包括: 标准化的软件接口 :用于与被测对象进行数据交换: Lua解析器:用 ...

  8. LINQ体验(2)——C# 3.0新语言特性和改进(上篇)

    整体来说.Visual Studio 2008和.NET 3.5是建立在.NET2.0核心的基础之上,.NET2.0核心本身将不再变化(假设不了解.NET2.0的朋友,请參看MSDN或者一些经典的书籍 ...

  9. C# 3.0新语言特性和改进

    体来说,Visual Studio 2008和.NET 3.5是建立在.NET2.0核心的基础之上,.NET2.0核心本身将不再变化(如果不了解.NET2.0的朋友,请参看MSDN或者一些经典的书籍) ...

最新文章

  1. 全面屏适配方案,终极版,华为隐藏导航栏解决方案
  2. 以下用于数据存储领域的python第三方库是-『爬虫四步走』手把手教你使用Python抓取并存储网页数据!...
  3. codeforces 229C
  4. Hibernate+mysql 中文问题解决方案.
  5. 不均衡数据集采样1——SMOTE算法(过采样)
  6. 事件循环中的宏任务和微任务执行顺序
  7. 深度学习实践指南(一)—— 卷积和池化
  8. 中国移动DNS IP地址大全(32个省)
  9. 注册苹果开发者账号遇到问题汇总
  10. pyautogui图形识别-confidence,grayscale
  11. 手写英文单词识别(1)
  12. VS2012 启动鼠标无法移动问题(个例)解决方案。
  13. LeetCode_904 水果成篮
  14. 亚马逊做精品选品怎么选?
  15. 2020.08.14日常总结——Trie树的实际应用
  16. ctf web shell
  17. OSError: [WinError 216] 该版本的 %1 与您运行的 Windows 版本不兼容。
  18. 如何提高百度指数,快速打造一个高权重网站
  19. mac安装jdk和maven以及环境配置
  20. 06-一些键鼠和页面操作

热门文章

  1. Oracle字符集讨论(转)
  2. 蓝牙心率检测仪涉及到的主要硬件组成
  3. PostgreSQL时间加减
  4. 基本运算电路之---反向比例运算电路(1)
  5. scratch编写游戏:火柴人避开防守投篮
  6. UDF:一个通过日期计算星座
  7. 首曲线、计曲线、间曲线和助曲线
  8. UnicodeDecodeError: 'gbk' codec can't decode byte 0x91 in position 8: illegal multibyte sequence
  9. 联想服务器系统改成win7,联想Win8系统换成Win7的步骤
  10. dlna 电脑连r1_pc 电脑如何投屏到电视? DLNA