即是否存在 ((a))
可以求值
Elisp:
Elisp 的调用表达式中第一项必须是 lambda 表达式或者函数名符号
(defun a () (lambda () 1))
;;=> a
(funcall (a))
;;=> 1
Racket
(define (a) (λ () 1))
((a))
;;=> 1
1 个赞
也就是说emacs的解释器无法做到。感谢指导
说起来,C语言不使用循环和跳转,也不定义递归函数,制造循环或许也是可行的。C里面的循环和跳转是严格对应跳转指令的,函数也严格对应调用指令,这两类指令以外是不存在第三类本地跳转的。然而,如果允许操作系统层面的操作,可以直接控制mmu,那么,程序结束时,把它的代码段所在的页的首地址映射成此时进程的指令地址,然后刷新icache,此时icache抓到的指令就是从原来的代码段首地址开始抓,这样不停地滑动地址,就可以达到循环的效果了。代码看起来应该是这样:
__attribute__((noreturn)) void f(void)
{
/* do something here */
// slide page address back
map_page(to_phys_addr(f), END);
// flush icache
__builtin___clear_cache(f, f + PAGE_SIZE);
barrier();
END:
}
1 个赞
有点 6,我研究一下去。
当时写的时候没考虑这么多,也许拿个更高级的语言举例更好,比如 Python
Tcl 也可以 :
proc a {} {lindex 1}
# => {}
[list [list a]]
# => 1
然而它的机制和 Lisp 是不一样的。继续实验会发现:
[list [list [list [list a]]]]
# => 1
[list [list [list [list [list [list a]]]]]]
# => 1
这是因为在 evaluate 的时候, 会强制取 list 的第一个元素的字符串表示,并将其作为命令名。这时它已经不再是(准确来说,是不再表示为)一个 list 了。
如果要用「更像」Lisp 的匿名函数写法,那就是:
set a [list {} {lindex 1}]
# => {{} {lindex 1}}
apply $a
# => 1
不对,好像已经歪楼了(逃
2 个赞