HY Lisp 读取宏(reader macro)学习

在学习HY lisp语言的时候HY编程快速入门实践课第三章 HY宏入门-CSDN博客,学习到了读取宏(reader macro),尝试将其概念弄明白。

首先,读取宏是Lisp语言中都有的一种概念,所以可以通过任意一种Lisp语言的文档来学习。因为HY的文档比较简单(篇幅少),所以准备结合Common Lisp、On Lisp等来进行学习。

在 Lisp 表达式的一生中,有三个最重要的时刻,分别是读取期(read-time),编译期(compile-time) 和运行期(runtime)。运行期由函数左右。宏给了我们在编译期对程序做转换的机会。而读取宏(read-macro),它们在读取期发挥作用。本段文字来源:第 17 章 读取宏(read-macro)_w3cschool

读到这里,终于明白了它为什么叫读取宏,原来是在读取时起作用的啊!

这样看来,读取宏就有点类似于宏定义(宏替换)了,比如单引号'就是quote,(quote a) 可以简写成'a 。Lisp里的普通宏也可以完成类似的工作,我们熟知的C语言里的宏定义,也是做了类似的工作。

那么为什么还要单独定义一个叫读取宏的概念呢? 这正是Lisp的的强大而独特之处:读取宏是可以嵌套的。比如(quote (quote a)) 可以简写成''a ,用普通宏实现宏替换,在嵌套的时候可能就会出错,而无法稳定实现功能。同样的C语言的宏定义也无法实现自己对自己的嵌套。

当然HY里对读取宏的实现没有像其它Lisp那么完全,比如它不能实现任意字符定义,而是需要像C的宏定义那样,以#开头。例子:

(defreader do-twice(setv x (.parse-one-form &reader))`(do ~x ~x))#do-twice (print "This line prints twice.")

然后就会看到print语句执行了两次:

=> #do-twice (print "This line prints twice.")
This line prints twice.
This line prints twice.
 

结合前面讲到的,Lisp在读取期(read-time),编译期(compile-time) 和运行期(runtime)三个时期都可以实现循环和嵌套,这极大的增强了Lisp的自由度,可以说Lisp是能力最强大的语言,这样或许不太准确,因为只要是图灵完备的语言,基本都能完成所有的任务,应该说Lisp是最接近人类思维的一种语言。我们想像一下,不管我们是读一个计划书,制定一个计划书,执行一个计划书的时候,是不是都可以重复(嵌套)我们的行为? 比如反复读,反复写,反复实践? 任何一个步骤如果有问题,都可以定位到该问题并反复执行? 

计算机最强大的地方就是快速重复工作,Lisp语言最强大的地方就是在任何时候,不管是读取、编译还是运行期,让计算机快速重复工作!

Lisp语言是最接近接近人类思维方式的一种语言,但是它的缺点也很明显,那就是它的代码是反人类思维,是最难读懂的一种语言。Basic语言(最开始的basic语言),能读懂英文的人,就大致能读懂程序。到了C语言和Pascal,不熟悉该语言语法的人,就有点难读懂,但结合注释,大致知道这一段代码是干什么的。而Lisp的代码,没学过的几乎肯定看不懂。我不知道Lisp高手过一段时间是否还能看懂自己写的代码,因为我还没到高手那个段位。我目前是连手册里的例子代码看起来都磕磕绊绊..... 

没有比较就没有伤害, 读完Lisp代码再看其它语言,不管是C还是汇编,都感觉清新可爱了呢,这也算是附加回报吧。

附录:

代码学习

(defreader matrix(.slurp-space &reader)(setv start (.getc &reader))(assert (= start "["))(.slurp-space &reader)(setv out [[]])(while (not (.peek-and-getc &reader "]"))(cond(any (gfor  c " \t"  (.peek-and-getc &reader c)))None(.peek-and-getc &reader "\n")(.append out [])True(.append (get out -1) (.parse-one-form &reader))))(lfor  line out  :if line  line))

这段代码是一个自定义的读取器(reader)函数,设计用于从一个输入源(如文件或字符串)中解析出嵌套列表(列表的列表)的结构。它采用了类似Scheme或Clojure中读取宏(reader macros)的语法和逻辑,但使用了Python风格的语法和假设的一些函数(如.slurp-space.getc.peek-and-getc.append.parse-one-form等),这些函数在标准的Python中并不直接存在,但可以理解为是某个自定义的读取器环境(可能是基于某种解析库或自定义实现的)提供的接口。下面是对这段代码的详细解析:

  1. 函数定义defreader matrix 定义了一个名为matrix的读取器函数。

  2. 跳过空白.slurp-space &reader 调用可能是为了跳过输入流(&reader)中的任何空白字符(如空格、制表符等),准备开始读取实际的列表内容。

  3. 读取起始符setv start (.getc &reader) 读取一个字符作为开始,并通过assert (= start "[")确认这个字符是左方括号[,表示一个列表的开始。

  4. 再次跳过空白:再次调用.slurp-space &reader以跳过可能的空白字符。

  5. 初始化输出列表setv out [[]] 初始化一个包含空列表的列表,用于存储解析出的嵌套列表。

  6. 循环读取内容:通过一个while循环,持续读取输入直到遇到结束符]。循环体内使用cond结构(类似于Lisp的cond或Python的if-elif-else)来处理不同的读取情况:

    • 如果读取到的字符是空白字符(通过gfor循环和any函数检查),则忽略该字符(None操作)。
    • 如果读取到换行符\n,则在out列表中添加一个新的空列表,以表示新的一行或新的子列表的开始。
    • 如果上述条件都不满足,则调用.parse-one-form &reader来解析当前位置的“一个表单”(可能是一个数字、字符串、列表等),并将其添加到当前子列表中。
  7. 返回结果:最后,通过一个lfor循环(可能类似于列表推导或for循环,但专门用于列表)遍历out列表,并只返回那些非空的子列表(通过:if line条件)。这一步可能是为了过滤掉由于换行符而额外添加的空列表。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.xdnf.cn/news/1472477.html

如若内容造成侵权/违法违规/事实不符,请联系一条长河网进行投诉反馈,一经查实,立即删除!

相关文章

完全理解C语言函数

文章目录 1.函数是什么2.C语言中的函数分类2.1 库函数2.1.1 如何使用库函数 2.2自定义函数 3.函数的参数3.1 实际参数(实参)3.2 形式参数(形参) 4.函数调用4.1传值调用4.2 传址调用4.3 练习 5.函数的嵌套调用和链式访问5.1 嵌套调…

【总线】AXI4第八课时:介绍AXI的 “原子访问“ :独占访问(Exclusive Access)和锁定访问(Locked Access)

大家好,欢迎来到今天的总线学习时间!如果你对电子设计、特别是FPGA和SoC设计感兴趣,那你绝对不能错过我们今天的主角——AXI4总线。作为ARM公司AMBA总线家族中的佼佼者,AXI4以其高性能和高度可扩展性,成为了现代电子系统中不可或缺的通信桥梁…

spring mvc学习

第四章 Spring MVC 第一节 Spring MVC 简介 1. Spring MVC SpringMVC是一个Java 开源框架, 是Spring Framework生态中的一个独立模块,它基于 Spring 实现了Web MVC(数据、业务与展现)设计模式的请求驱动类型的轻量级Web框架&am…

T100-XG查询报表的开发

制作XG报表 1、注册程序 azzi900 首先现将程序注册一下,在内部构建基础代码档。 2、注册作业 azzi910 也是直接新增一个,作业跟程序绑定一下。 3、T100签出规格程序 这个时候应该是没签出的,首先将规格迁出。 4、T100画面产生器 规格迁出之后,这个时候还需要生成一个画…

小型气象站在现代农业中的应用与前景

随着科技的飞速发展,智慧农业已成为现代农业发展的重要趋势。在这一背景下,小型气象站作为智慧农业的重要组成部分,正逐渐展现出其独特的价值和广阔的应用前景。本文将从小型气象站的定义、功能、应用案例以及未来展望等方面,探讨…

数据库数据修改和删除操作详解

目录 🎃摘要 1. 数据库数据修改概述 2. 数据更新操作 2.1MySQL数据更新示例 3. 数据删除概述 4.使用DELETE进行数据删除 4.1 DELETE的基本语法 4.2 DELETE的使用场景 4.3 DELETE示例 5. 使用TRUNCATE进行数据删除 5.1 TRUNCATE的基本语法 5.2 TRUNCATE的…

谷粒商城学习-11-docker安装redis

文章目录 一,拉取Redis镜像1,搜索Redis的Docker镜像2,拉取Redis镜像3,查看已经拉取的镜像 二,创建、启动Redis容器1,创建redis配置文件2,创建及运行Redis容器3,使用docker ps查看运行…

docker-compose构建运行管理容器

win10安装docker并用docker-compose构建运行容器较为简单,只需要在程序和功能中开启Hyper-V虚拟功能,然后安装docker desktop即可。 创建文件目录及配置文件 在D盘新增app文件夹,创建dockerfile、docker-compose.yml、logs dockerfile # …

Elasticsearch实战教程:如何使用集群索引数据来进行统计多个数据?

🎬 鸽芷咕:个人主页 🔥 个人专栏: 《C干货基地》《粉丝福利》 ⛺️生活的理想,就是为了理想的生活! 引入 Elasticsearch聚合查询是一种强大的工具,允许我们对索引中的数据进行复杂的统计分析和计算。本文将详细解释一…

九、SSM整合介绍-Eclipse整合(2)

🌻🌻目录 一、SSM 整合二、SSM整合入门三、整合的实现3.1、创建数据库以及表3.2、创建项目3.3、依赖3.4、项目配置3.5、项目测试 一、SSM 整合 1、整合:将多种框架合并到一起,完成项目需求 2、SSM整合:Springmvc Spri…

竞赛选题 协同过滤电影推荐系统

文章目录 1 简介1 设计概要2 课题背景和目的3 协同过滤算法原理3.1 基于用户的协同过滤推荐算法实现原理3.1.1 步骤13.1.2 步骤23.1.3 步骤33.1.4 步骤4 4 系统实现4.1 开发环境4.2 系统功能描述4.3 系统数据流程4.3.1 用户端数据流程4.3.2 管理员端数据流程 4.4 系统功能设计 …

介绍一款Java开发的商业开源MES系统

介绍一款Java开发的开源MES系统,万界星空科技开源的MES系统。该系统基于Java开发,具有广泛的适用性和高度的可定制性,能够满足不同行业、不同规模企业的智能制造需求。 一、系统概述 万界星空科技开源的MES系统是一款面向制造企业车间执行层…

代码随想录算法训练营第71天:路径算法[1]

代码随想录算法训练营第71天:路径算法 ‍ Bellman_ford 算法精讲 卡码网:94. 城市间货物运输 I(opens new window) 题目描述 某国为促进城市间经济交流,决定对货物运输提供补贴。共有 n 个编号为 1 到 n 的城市,通过道路网络…

笔记本休眠后自动关闭所有程序

关于主动进入休眠后,笔记本过一晚第二天会关闭所有程序,开始还以为,笔记本没电了,或者公司停电了导致笔记本没电关机,排查后发现不是。。。 原因是笔记本电脑默认设置休眠20分钟后自动关闭硬盘。 解决方案&#xff1a…

抖音短视频矩阵系统源代码开发-oem搭建

抖音矩阵号管理系统是一个综合性平台,旨在为企业、机构和个人提供全面的抖音账号管理服务。系统具备以下核心功能: 1. 用户管理:本系统支持多用户操作,允许管理员为每个用户分配专属的抖音矩阵号,实现个性化管理。 2.…

一站式采购!麒麟信安CentOS安全加固套件上架华为云云商店

近日,麒麟信安CentOS安全加固套件正式上架华为云云商店,用户可登录华为云官网搜索“CentOS安全加固”直接采购,一站式获取所需资源。 麒麟信安CentOS安全加固套件已上架华为云 https://marketplace.huaweicloud.com/contents/9fe76553-8d87-…

山东益康,聚焦绿葆医院场景媒体,用爱服务人类健康

山东益康集团创建于1983年,发展成为集药品研发生产、销售、特医功能食品、精细化工、医疗防护产品等多产业经营为一体的省级企业集团。益康集团紧跟国家发展战略,满足民众日益增长的健康需求,将食品生产向特医保健功能食品转型升级&#xff0…

智能家居安防系统教学解决方案

前言 随着科技的不断进步和智能家居概念的深入人心,智能家居安防系统作为智能家居领域的重要组成部分,其重要性日益凸显。智能家居安防系统不仅能够提供环境和人员的监测功能,还能够采取措施降低或避免人员伤亡及财产损失。因此,…

使用大漠插件进行京东联盟转链

由于之前开发了一套使用api转链的接口在前面几个月失效了。因为京东联盟系统升级,导致之前可以转的链接现在必须要升级权限才可以。但是升级条件对于我们这些自己买东西转链想省点钱的人来说基本上达不到。 所以,基于这种情况。我之前研究过大漠插件&am…

Twitter群发消息API接口的功能?如何配置?

Twitter群发消息API接口怎么申请?如何使用API接口? 为了方便企业和开发者有效地与用户互动,Twitter提供了各种API接口,其中Twitter群发消息API接口尤为重要。AokSend将详细介绍Twitter群发消息API接口的功能及其应用场景。 Twit…