Forwarded from duangsuse Throws
#dev #JavaScript #Haha 草,我竟然做出来了……
一个车夫,赶着1辆马车,车上坐着5个人,每人拿着5个袋子,每个袋子里装着5只大猫,
每只大猫带5只小猫,每只小猫带着5只老鼠干粮
问:这道题里一共有多少条腿? 😂
衬衫的价格是 9 磅 15 便士。ES6。
一个车夫,赶着1辆马车,车上坐着5个人,每人拿着5个袋子,每个袋子里装着5只大猫,
每只大猫带5只小猫,每只小猫带着5只老鼠干粮
问:这道题里一共有多少条腿? 😂
衬衫的价格是 9 磅 15 便士。ES6。
constanswer = cheche(1) //13104
laoshu = n => n*4,
mao = n => laoshu(n)*5 + 4,
bigmao = n => mao(n)*5 + 4,
daizi = n => bigmao(n)*5,
ren = n => daizi(n)*5 + 2,
cheche = n => 2 + ren(5);
Forwarded from 憨憨的碎碎念 | #成为打工人 (Channel Helper)
===== 评论区 =====
duangsuse: https://tttttt.me/dsuset/7251
wuhang2003 - 疯狂...: (➤duangsuse) 同学给的答案是 15516,某搜题软件提供的答案是 15512 ,怎么说这差距也太大了🌚
duangsuse: https://tttttt.me/dsuset/7251
constanswer = cheche(1) //13104
laoshu = n => n*4,
mao = n => laoshu(n)*5 + 4,
bigmao = n => mao(n)*5 + 4,
daizi = n => bigmao(n)*5,
ren = n => daizi(n)*5 + 2,
cheche = n => 2 + ren(5);
wuhang2003 - 疯狂...: (➤duangsuse) 同学给的答案是 15516,某搜题软件提供的答案是 15512 ,怎么说这差距也太大了🌚
Telegram
duangsuse Throws
#dev #JavaScript #Haha 草,我竟然做出来了……
一个车夫,赶着1辆马车,车上坐着5个人,每人拿着5个袋子,每个袋子里装着5只大猫,
每只大猫带5只小猫,每只小猫带着5只老鼠干粮
问:这道题里一共有多少条腿? 😂
衬衫的价格是 9 磅 15 便士。ES6。
const
laoshu = n => n*4,
mao = n => laoshu(n)*5 + 4,
bigmao = n => mao(n)*5 + 4,
daizi = n => bigmao(n)*5,
ren = n…
一个车夫,赶着1辆马车,车上坐着5个人,每人拿着5个袋子,每个袋子里装着5只大猫,
每只大猫带5只小猫,每只小猫带着5只老鼠干粮
问:这道题里一共有多少条腿? 😂
衬衫的价格是 9 磅 15 便士。ES6。
const
laoshu = n => n*4,
mao = n => laoshu(n)*5 + 4,
bigmao = n => mao(n)*5 + 4,
daizi = n => bigmao(n)*5,
ren = n…
https://github.com/itorr/homo/blob/master/homo.js#L1 #JavaScript #code
核心代码,首先我们有一个类似这样的表,
核心代码,首先我们有一个类似这样的表,
eval(xs[i]) == i
: ["1", "2"]function divmod(a, b) { return [Math.trunc(a/b), a%b]; }开始我还以为是自动构造数学表达式然后 filter 呢……
function ordFinder(xs, cmp, is_descending = false) {
const sorted = is_descending? xs.sort((a, b) => b-a) : xs.sort();
return function finder(n) {
for (let x of xs) if (cmp(x, n)) return x;
};
}
const findMaxLT = ordFinder(predefined, (a, b) => a < b, true);
function demolish(num) {
if (typeof num != "number") return "";
if (num < predefined.length) return predefined[num];
let [k, div] = divmod(num, findMaxLT(num) );
return `({demolish(k)}*{div}+{deomolish(mod)})`. replace(/\*\(1\)/, "") //*1=itself
}
GitHub
homo/homo.js at master · itorr/homo
💩「恶臭数字论证器」数字恶臭化工具. Contribute to itorr/homo development by creating an account on GitHub.
#web #PLT #JavaScript #zhihu https://www.zhihu.com/question/385711203#write
牛逼啊,竟然还扯出了 extonic object, 稀疏数组, 2^53-1 一大堆术语
牛逼啊,竟然还扯出了 extonic object, 稀疏数组, 2^53-1 一大堆术语
Zhihu
为什么js没有array初始大小和扩容的概念? - 知乎
在谈论js时,很少听人谈论array,object等引用型数据类型初始大小以及扩容的问题?这是为什么?也没有听…
function* readSourceTable(text) { //< obsoleted
let entries = text.split("\n\n");
for (let entry of entries) {
let entryList = [];
let key = null; let content = "";
for (let line of entry.split("\n").map(it => it.trim())) {
if (line.length == 0) continue;
if (line.endsWith(":")) {
if (key != null) entryList.push([key, content]);
key = line.substring(0, line.length-1); content = "";
} else content += `${line}\n`;
}
entryList.push([key, content]);
yield entryList;
}
}
#JavaScript #web 丢掉的代码,虽然也不怎么厉害Forwarded from dnaugsuz
https://tttttt.me/dsuse/11472
这个是 js 的动态尾递归优化(迫真)
这个是 js 的动态尾递归优化(迫真)
Telegram
duangsuse::Echo
推荐一个 tco 函数 #JavaScript #FP
function _argveq(xs, ys, rb_i) { var i = rb_i | Math.min(xs.length,ys.length);
if(xs.length !== ys.length) return false;
while (i!==0) { --i; if(xs[i] != ys[i]) return false; }
return true;
}
// op tailrec must rewrite its…
function _argveq(xs, ys, rb_i) { var i = rb_i | Math.min(xs.length,ys.length);
if(xs.length !== ys.length) return false;
while (i!==0) { --i; if(xs[i] != ys[i]) return false; }
return true;
}
// op tailrec must rewrite its…
补充一句: #Python #PLT #cs 红姐 其实是 github.com/thautwarm
https://pythonhunter.org/episodes/ep11
https://github.com/anqurvanillapy
另外 ANQUR 也是 Python 大佬
#JavaScript 的 贺老 就是贺师俊、 阮老师 就是 阮一峰
这些是昵称/尊称。
https://pythonhunter.org/episodes/ep11
https://github.com/anqurvanillapy
另外 ANQUR 也是 Python 大佬
#JavaScript 的 贺老 就是贺师俊、 阮老师 就是 阮一峰
这些是昵称/尊称。
GitHub
thautwarm - Overview
Casting a fireball. thautwarm has 236 repositories available. Follow their code on GitHub.
duangsuse::Echo
幸好,我已经准备好弄内部 DSL 版的了😥
中午还没吃饭,那就不吃了,最近浪费时间第一的实践...
#JavaScript 其实最开始我是不打算用 fold 解释器的,打算直接用 eval() 处理变成 clickingOn("wtf").addsClass("") 这种形式的代码,为此还定义了一个
foldReplace(/(\S+)\s+(\S+)("[^"]*")?/, (a,b,c) => a+capitalize(b)+c?
但是发现这样没法区别处理 "" 里的东西,不得不换成兼容 ES5 的 RegExp sticky flag 分词法。
总之,这次感觉血亏,跟着一个30岁,还只会前端、冒鬼点子的大叔,也没学到写CSS。
嗯…… 也不全对,学到了个 requestAnimationFrame((t_ms) => void) 算 start/elapsed
还有魔怔的 +function(){}() 等于 (function(){})() IIFE 技巧
#JavaScript 其实最开始我是不打算用 fold 解释器的,打算直接用 eval() 处理变成 clickingOn("wtf").addsClass("") 这种形式的代码,为此还定义了一个
foldReplace(/(\S+)\s+(\S+)("[^"]*")?/, (a,b,c) => a+capitalize(b)+c?
(${c})
:"", "apple fd") function capitalize(s) { return (s=="")?"" : s[0].toUpperCase()+s.substr(1, s.length); } function foldReplace(re, op, input) { var text=input; var matched=false; do { matched=false; text = text.replace(re, (_, ...args) => { matched=true; return op(...args); }); } while(matched); return text; }但是发现这样没法区别处理 "" 里的东西,不得不换成兼容 ES5 的 RegExp sticky flag 分词法。
总之,这次感觉血亏,跟着一个30岁,还只会前端、冒鬼点子的大叔,也没学到写CSS。
嗯…… 也不全对,学到了个 requestAnimationFrame((t_ms) => void) 算 start/elapsed
还有魔怔的 +function(){}() 等于 (function(){})() IIFE 技巧
Forwarded from RWTG9Y4's STDOUT
#ce #plt #JS #DontKnow 在 #JavaScript 的一个
(其中 fetch 返回一个 Promise,且这个 Promise 一定是成功的)
duangsuse:
await 的话等价 yield 执行权给 awaiter ,成功了 return it ,大概是 Promise<String> ?
reply:
正常 async 函数返回值也是
other:
如果返回的是promise那么还得await或是then
reply:
并不需要,Promise 套娃是会自动解开的
duangsuse:
[In reply to duangsuse]
呃……想起来了,async awaiter 其实会自动 await yield 的 Promise ,而 return 也是一种 yield
duangsuse:
[In reply to reply]
duangsuse:
[In reply to duangsuse]
亦可简写为
果然是 try-catch 时控制流易跑偏……看来在协程continuation的实现方面结构化异常处理需要注意啊
duangsuse:
[In reply to reply]
感觉你这个和举的例子有点区别啊…… 举的例子里 return 是实际执行的最后一条语句
第一个…… 不对,看起来是我默认错了
最后一行和实际末语句是有区别的,如在
尾调用优化也是
duangsuse, [13.01.21 11:06]
try {} 里的 return 语句居然还能前置执行 finally {} ,涨知识了
之前哪里能用到这么多 try 块……
await 休眠当前函数实现的不错,看来这个问题是问“控制流什么方法可以在 return 前加逻辑”啊
回答本身是执行顺序问题。如果直接 return Promise 会被 awaiter 处理,类型上也没错
async function
中,请问在什么情况下 return fetch(...)
和 return await fetch(...)
会有区别?(其中 fetch 返回一个 Promise,且这个 Promise 一定是成功的)
duangsuse:
async function
相当于一个可带 awaiter 的 function*
,封装为 Promise
直接 return Promise 大概会得到二层的这个await 的话等价 yield 执行权给 awaiter ,成功了 return it ,大概是 Promise<String> ?
reply:
正常 async 函数返回值也是
Promise<string>
哦(注: fetch() resolve 后是 stringother:
如果返回的是promise那么还得await或是then
reply:
并不需要,Promise 套娃是会自动解开的
duangsuse:
[In reply to duangsuse]
呃……想起来了,async awaiter 其实会自动 await yield 的 Promise ,而 return 也是一种 yield
duangsuse:
[In reply to reply]
async function op1() { return Promise.resolve(100); }
async function op2() { return 100; }
for (let op of [op1,op2]) op().then(console.log); //100 x2
function foldN(n, op, x) { var acc=x; for (var i=0;i<n; i++) {acc = op(acc);} return acc; }
foldN(4, (x) => Promise.resolve(x), 100).then(console.log)
reply:try { return op1(); } finally { op2(); }里 op1() 先执行
try { return await op1(); } finally { op2(); }里 op2() 先执行
duangsuse:
[In reply to duangsuse]
亦可简写为
const puts=console.info;
const op1 = async()=>Promise.resolve(100), op2 = async()=>100;
for (let op of [op1,op2]) op().then(puts);
foldN(4, v=>Promise.resolve(v), 100).then(puts);另外一般内部实现的 awaiter 亦可这么定义:
function __onestep(gen) {未实现 reject
let {value, done} = gen.next();
if (!done && value instanceof Promise) value.then(x => __onestep(gen.next(x)) );
else return value;
}
function __awaiter(gen) { return Promise((resolve, reject) => { resolve(__onestep(gen)); }; }
果然是 try-catch 时控制流易跑偏……看来在协程continuation的实现方面结构化异常处理需要注意啊
duangsuse:
[In reply to reply]
感觉你这个和举的例子有点区别啊…… 举的例子里 return 是实际执行的最后一条语句
第一个…… 不对,看起来是我默认错了
最后一行和实际末语句是有区别的,如在
() => { return 1; print(); }
里。尾调用优化也是
return thisOp();
是可变成循环, return thisOp()+1;
仍需保留调用栈duangsuse, [13.01.21 11:06]
try {} 里的 return 语句居然还能前置执行 finally {} ,涨知识了
之前哪里能用到这么多 try 块……
await 休眠当前函数实现的不错,看来这个问题是问“控制流什么方法可以在 return 前加逻辑”啊
回答本身是执行顺序问题。如果直接 return Promise 会被 awaiter 处理,类型上也没错
列一些有趣的社区项目 #math #listing #Java
https://www.desmos.com/calculator/i6fijibmbz
#GUI 系列:
https://github.com/darsam44/Mini-desmos (吐嘈: 真的不迷你)
https://github.com/DanielZhangD/Javmos
https://github.com/LitterallyTheCoolestGuy69/Desmos-But-Scuffed
#Python 转换/等式代码生成脚本系列:
https://github.com/MrNewdary/svg2desmos/blob/main/svg2desmos.py
https://github.com/anematode/parametrizer/blob/master/undeletable.py
https://github.com/allesspassig/despy/blob/master/despy.py
https://github.com/emily-yu/image-to-desmos OpenCV #cv
#music https://github.com/AlexApps99/MIDI2Desmos 听 MIDI 函数图系列...
多项式课系列:
https://github.com/galbar07/Desmos
https://github.com/yonatan555/Desmos-Polynom
https://github.com/JiangTianXiang/Grade-12-Calculus-Graphing-Calculator
https://github.com/WhoIsKatie/Javmos
https://github.com/TimChoy/javmos
https://github.com/DvirTomer/Desmos-Polynom
乱入:
https://github.com/andrewpareles/Calculator/blob/master/main.ml
https://github.com/Tuttivers/ExponentialSeekbar-sample/blob/master/NearMeSeekBar.kt#L75 #Kotlin #Android
https://mukunthag.github.io/SHM/ 振荡器什么的...
https://github.com/Rob--/root-approximations/blob/master/evaluatex.js#L190 #JavaScript #lib #parsing 几百行的符号代数系统...
可移植性/项目管理极差的 GUI:
https://github.com/Pi-Man/Graphing-Calculator/tree/master/Graphing-Calculator
https://github.com/RohanK22/cppmathtool
http://well-made-territory.surge.sh/Desmos.html
https://github.com/softchickenidiot/3D-Grapher/tree/master/3D Grapher
https://www.desmos.com/calculator/i6fijibmbz
#GUI 系列:
https://github.com/darsam44/Mini-desmos (吐嘈: 真的不迷你)
https://github.com/DanielZhangD/Javmos
https://github.com/LitterallyTheCoolestGuy69/Desmos-But-Scuffed
#Python 转换/等式代码生成脚本系列:
https://github.com/MrNewdary/svg2desmos/blob/main/svg2desmos.py
https://github.com/anematode/parametrizer/blob/master/undeletable.py
https://github.com/allesspassig/despy/blob/master/despy.py
https://github.com/emily-yu/image-to-desmos OpenCV #cv
#music https://github.com/AlexApps99/MIDI2Desmos 听 MIDI 函数图系列...
多项式课系列:
https://github.com/galbar07/Desmos
https://github.com/yonatan555/Desmos-Polynom
https://github.com/JiangTianXiang/Grade-12-Calculus-Graphing-Calculator
https://github.com/WhoIsKatie/Javmos
https://github.com/TimChoy/javmos
https://github.com/DvirTomer/Desmos-Polynom
乱入:
https://github.com/andrewpareles/Calculator/blob/master/main.ml
https://github.com/Tuttivers/ExponentialSeekbar-sample/blob/master/NearMeSeekBar.kt#L75 #Kotlin #Android
https://mukunthag.github.io/SHM/ 振荡器什么的...
https://github.com/Rob--/root-approximations/blob/master/evaluatex.js#L190 #JavaScript #lib #parsing 几百行的符号代数系统...
可移植性/项目管理极差的 GUI:
https://github.com/Pi-Man/Graphing-Calculator/tree/master/Graphing-Calculator
https://github.com/RohanK22/cppmathtool
http://well-made-territory.surge.sh/Desmos.html
https://github.com/softchickenidiot/3D-Grapher/tree/master/3D Grapher
Desmos
Final Project
duangsuse::Echo
#python #code #telegram #tool 修正tg desktop 的复制成员名太长
我开始讨厌学校里照本宣科了,如果不是因为不熟悉 #JavaScript 这种「动态语言」,怎么会写出如此执掌的代码……我太阳
学校的JS理应把重点,首先让他们写 deep copy 和 deep eq 之类熟悉{} 然后再科普ES6新语法,以及Babel,TypeScript 在完全无需考虑兼容这回事
DOM最少也要把 innerHTML 和 Text 的区别教了,别只AJAX下载html,省得一些人文H不分
学校的JS理应把重点,首先让他们写 deep copy 和 deep eq 之类熟悉{} 然后再科普ES6新语法,以及Babel,TypeScript 在完全无需考虑兼容这回事
DOM最少也要把 innerHTML 和 Text 的区别教了,别只AJAX下载html,省得一些人文H不分
duangsuse::Echo
#js 和EQ的风格很像了 🤔 ee.main=({n=1}, 奇偶=wKV({class: when(n.as(x=>x%2), "odd","even") }) )=> div( h1(奇偶, html`count is ${n}`), h2(html`2x is ${n.as(x=>x*2)}`), button(wOp({tap:n(x=>x+1)}), "👍") ) 感觉这种情况下EQ没什么竞争力? (不过EqvJS 的理论是与页面段「带变量合一」,而不是 "Reactivity"..…
在这个视频
函数风格的DSL #design 不是很新的概念(尽管在js界里是.. ),Flutter,ktCompose,我的TkGUI, 甚至蛤为的 ArkTS 都用它取代过XML
☝️一个框架能意识到 CSS,HTML -in-JS 对整个易用/复用性的必要,可以说是一种革命 ,因为它的设计重点从
当然,写法的不同也是主要竞争力,像 ArkTS 这个就滥用builder和this ,非常难看
EQ一开始也像Van一样主要负责“模板”,但后来也实现了 lists,when ,组件和CSS模块化
这个视频例子上,EQ的胜负处:
👍
- 统一的风格(甚至像独立于ES6的语言了),避免 func,const,return div() 的无味之争
- 没有
- 没有
- html格式化,很ES6
-
- 我不写 3:33 的那种滥用弱类型的代码😐 简洁,显然不是指能看懂的符号少
👎
- wOSK{} 三要素 没能显示出对组件设计的益处 (需求太常规,API的体系性无法体现。像 Van 这样到处 onclick 是意识不到该做
- 同样,因为EQ涉及三界(JS的带this管道,async load,ondiff,ease-efx,wOp-SSR事件上传,.) 所以只有 界0=wOSKita 是<100行的,与Van同为极简主义的我应该很丢脸?(x
- 在不用爬虫时写
-
— 在 4:09 上 —
👍
-
-
-
- 浏览器本就会“批量修改DOM” 再reflow ,EQ不会对数组以外重新检查 “vDOM变更”,再用setTimeout去哆嗦着赋值那些玩意。
- EQ自然支持 SSR(注水,wOp上传-HTML下载, ) 尽管未提供无DOM模式
😐
- 不用写 import tags,因为 evalFun 在运行或编译时支持了 this 作用域
-
- 不能
不能靠
因此,EQ里 wKV 是不需要靠返回原元素,来避免replace的
EQ选择的是
也因此对 [1,2,3] 和 [[1],[2]] 赋值,都是既不Memo(Van做到了),也不导致<text>外ul节点替换的,只是旧值被新值“合一”了
总之,VanJS 足够小,所以这个视频分析的相当全面 #recommend
可能在程序员看来,我每天都在写 “不能运行的代码”……
但这就是设计者做事的方法 🥳
函数风格的DSL #design 不是很新的概念(尽管在js界里是.. ),Flutter,ktCompose,我的TkGUI, 甚至蛤为的 ArkTS 都用它取代过XML
☝️一个框架能意识到 CSS,HTML -in-JS 对整个易用/复用性的必要,可以说是一种革命 ,因为它的设计重点从
@click.prevent
和 "reactivity" 这些花哨的东西,转移到UIUX的数据和操作上了当然,写法的不同也是主要竞争力,像 ArkTS 这个就滥用builder和this ,非常难看
EQ一开始也像Van一样主要负责“模板”,但后来也实现了 lists,when ,组件和CSS模块化
这个视频例子上,EQ的胜负处:
👍
- 统一的风格(甚至像独立于ES6的语言了),避免 func,const,return div() 的无味之争
- 没有
n=van.state(1)
, 变量随便加- 没有
.val
(按_currDep
捕获val访问) 和derive的概念,而是让事件选中(Eq.sel)变量,看起来更纯,低魔法- html格式化,很ES6
-
when()
很漂亮,在纯JS,html 里都能用- 我不写 3:33 的那种滥用弱类型的代码😐 简洁,显然不是指能看懂的符号少
👎
- wOSK{} 三要素 没能显示出对组件设计的益处 (需求太常规,API的体系性无法体现。像 Van 这样到处 onclick 是意识不到该做
btn(数组,)
复用, 以及该避免 onclick 可变时"escape" )- 同样,因为EQ涉及三界(JS的带this管道,async load,ondiff,ease-efx,wOp-SSR事件上传,.) 所以只有 界0=wOSKita 是<100行的,与Van同为极简主义的我应该很丢脸?(x
- 在不用爬虫时写
html
模板,稍微有点长-
wOp({tap:n(x=>x+1)})
选中了n变量,但放在 html`count is ${n(x=>x+1)}`
也可以— 在 4:09 上 —
👍
-
{x:0}.it.x
不负责保留旧值,也没 html _binds ,因此适合在NodeJS里用-
x0.it.to({x:1}, (A,B)=>B)
的「合一 unify」 适用于赋默认值、模式匹配等情况 🌠-
div$cls()
简写真的很CSS。EQ的风格就是DOM加糖- 浏览器本就会“批量修改DOM” 再reflow ,EQ不会对数组以外重新检查 “vDOM变更”,再用setTimeout去哆嗦着赋值那些玩意。
obj.it
就是EQ的“虚拟树-但无关HTML ”- EQ自然支持 SSR(注水,wOp上传-HTML下载, ) 尽管未提供无DOM模式
😐
- 不用写 import tags,因为 evalFun 在运行或编译时支持了 this 作用域
-
createElementNS()
的支持被复杂化为 {svg}=ee.use, 包含 svg,WebAudio 滤镜图- 不能
van.add(ul,state转节点)
,因为EQ必须支持爬虫和diff-特效,必须隔离JS,DOM,而不是靠跳帧检测全局states, 替换或删除其 _binds=[元素,函数,deps..] , 再在节点已移除时"GC"不能靠
ul( ()=>del? null : li() )
修改子节点,只有“when,as=filter函数”能做GC因此,EQ里 wKV 是不需要靠返回原元素,来避免replace的
EQ选择的是
Node 和 Object.it
“合一”,而不是 shallowRef()
的字典,所以它的 diff 不是在树内vars被拍平后,靠跳帧检测,而是在 JS对象图。也因此对 [1,2,3] 和 [[1],[2]] 赋值,都是既不Memo(Van做到了),也不导致<text>外ul节点替换的,只是旧值被新值“合一”了
总之,VanJS 足够小,所以这个视频分析的相当全面 #recommend
可能在程序员看来,我每天都在写 “不能运行的代码”……
但这就是设计者做事的方法 🥳
YouTube
How UI Frameworks Actually Work
A look at VanJS (https://vanjs.org/) and some core concepts such as state reactivity and DOM templating.
Check out Van's code base here: https://github.com/vanjs-org/van.
💬 Topics:
- How to use VanJS;
- What is reactive state;
- JSX and alternativess;
-…
Check out Van's code base here: https://github.com/vanjs-org/van.
💬 Topics:
- How to use VanJS;
- What is reactive state;
- JSX and alternativess;
-…
duangsuse::Echo
#js #code 再来说个有趣的:动态作用域 🥰 a=3 - f(a)=a+1 f(1), a //2, 3 >请把程序写成数组的形式 (也就是“更易做”正则替换) with(DSL) $dyn=[ [a,3], [f, [[a], [0, [a],1,['+'] ]] ], [r0, [0, 1,[f]], [a]] ] DSL=new Proxy({},{get:(o,k)=>k, has:(o,k)=>k[0]!='$'}) 在这个解释器里,$=, ()=>[] 就是内联宏啦,反正函数不能跳转…
cg($dyn)
生成了 ()=>(a=3,f=(a)=>(a+1),r0=[f(1),a])
,运行正常- just(a)那再来一个
- f()=a
f
just(0)()
with(DSL)$lex=[[],
[just, [[a], [f,[[],[a] ]], [f] ]],
[f,[0, 0,[just]]],
[0, f] //“类型推导”差到不能直接调用
]
()=>(just=(a)=>(f=()=>(a),f),f=just(0),f())
是0而不是3实际上,()=> 的值会捕获上1层参0='a' 。在动态域里,大家会把"自由变量a"连着全局表整个copy一份
设想下 cg.bind(kv={},ast) 每层都有一张“表”是什么图景。算+-*/可都是要递归的
列表处理不熟的人都能想出
List<Map>, Map<K,List>
并觉得后者“很快”,而C++《龙书》则建议单个KV、每层调用栈暂swap()下冲突的K (这么简单的做法 却放错顺序了)而JS是以前者链查找重写重载
[{a:1}, {b:2},kv={c:3}].reduce((A,B)=>(B.__proto__=A,B))
这些算法,都是在一个错的心智模型下选择的技术。 参数/局部/捕获的数目是固定的,只有$0$1 的指针可言,AST里哪里有全局键(导入)外的“变量名”??在通过bash,Lua.org 弄清这点原理前做事,会把一切搞砸。🌚 但这也是知 名的GADT+HOAS(的最 通 用 的 De Bruijn 指针).
>请把 at a=1, a+2 写成匿名调用的形式
a就是一个可以重绑定的“洞”, Vue都会:
add=(a,b)=> ()=>[a(),b](Fn1:[x] add(x, 2)) (1)
f=assign(()=>[0, ()=>arg[0],2,[add] ]),{arg:[]})
//用“语法树模板”表示箭头函数call=(f,...a)=>(f.arg=a, cg(f))call(匿名f,1)
#statement 变量关系式编程天天用 文化输出成解构+类型体操+Reactive响应算式/约束逻辑后就变🐮逼了,而函数式的闭包+回调(栈转堆,return地址转闭包) 输出变成协程/
yield{(then=>),}
后也TM🐮逼了,内联return变goto变尾递归时,又比break更平等了,纯的 if(a,a,puts) a&&puts()
又和自动闭包宏不一样了文本-AST-Scratch VM_IR-SSA-节点图 又隔离了,AST就不能是赋值图了。 这叫原地踏步式的前沿🥰 怀旧你🦄呢
(Kt 1..2对int,long 乃至Iter,Seq都有不同的(模板性)重载 ,连(Java8 stream 里也有的)去除装箱都没推广到语言层面。
a=x?.f()
的?像一个修饰器,在f代表语句时外提为(Cont
的捕获:switch化也需要) _f=x?f(x):x; a=_f
而反观那些ANTLR,YaCC 会逼你再来浅先遍历1次,以解析栈内存,否则会增大解释器开销--因为它们是靠LALR等“虚拟机”而不用现成的调用栈递归。 小众领域的白象总是揉杂到夸张
其他玩法:
$=(...x)=>cg([[],...x])()
with(DSL)$([x,3], [a,1,x])
with(DSL)$([0, 1, [[x], [x]] ])
with(DSL)$([0, 1,[[x], [0, 2,[[y], [0,x,y,'+']] ] ]] )
cg()
短的原因是,它只是把语法解构再构了一遍(或者说穷举了输入=>输出的对应性),就像 noop=(a,b=0)=>a==0? b :移动
一样基础但这就是编程语言的本质: 如果抢了应用或功能点的风头,沉迷于无尽循环的轮子,那必然是种设计错误
想测试自己元编程能力,可以做些改进:
1. vararg和可选参数, forEach, 自动支持await
2. 把“静态”检查的f(a,b,c) 回退到弱类型 [..,3,f] 且不与既有AST冲突
3. 把重赋值扩展到py式
(,自动新建变量)=>,,
,变量表可以直接用原型链,注意 f(a=[]) 是能被f修改的4. 常量折叠,循环展开
[for,x, [[1,2,3]], [0,[x,print]] ]
为3次print5. 用词法域,把调用和递归转为push;|用CPS,把调用栈闭包成堆内链表 ,转化到这一步代码就剥离开JS的ABI了
台湾的翻译的heap,stack就是从 malloc(), alloca(stack) 意译的吧
函数级的存储空间就像push(struct),是能静态计算。
btw. 惰性Proxy(可变<函数>) 是环形依赖的组织方法。
f=>(a,b)=>a? f(a-1,b+1):b
你可以试试用 fref(f=>f).set( Y组合子)
和蹦床函数(伪递归) 计算下如果不会写,可以用「费曼算法」:上面说了
>请把程序写成数组的形式
🥰GPT就是费曼算法的一种实现,但它不能替你踩坑啊。
很想给点引文:mal lambda书, decaf-lang C书, Craft 书, 闭包详解, JVM R佬科普, c4:极简栈解释器,minipy
Lox实现图解, js工具库, astexpo, godbolt.org , tio.run , 语言花名册
👍20页纯示例 http://rigaux.org/language-study/syntax-across-languages.html#:~:text=Bags%20and%20Lists
http://rigaux.org/language-study/scripting-language/#:~:text=compile%20what%20must%20be
其他 code.golf:
重构浣熊 多语言
https://blog.vero.site/post/noulith#:~:text=The%20Cube
https://github.com/eclipse-archived/ceylon-lang.org/blob/master/blog/2015-10-27-why.md#reified-generics
https://ruslanspivak.com/lsbasi-part1/
但那么多都TMD在讲BNF讲分词,还有人把py的缩进往回{}改 😅中文圈就没个做基建的
(正则吃数|读树)都不会是吧。 BNF也就比XML好看一丁点,单知道输入数据长什么样,对理解语言做元编程帮助很少
#haskell 上也有
https://okmij.org/ftp/tagless-final/index.html#:~:text=class%20Symantics 称为GADT https://stackoverflow.com/questions/33928608/typed-abstract-syntax-and-dsl-design-in-haskell
我是说
Lit(Int): T<Int>
Add(A,B): T<Int>
toStr(this:T<*>): T<Str>
本质是把fun提升为class。套一层Lit<R>是方便另加接口,比如统一能eval():R ,当然这也是OOP比FP扩展性强的一个中心思想
能直接DSL或弱类型when就不要做无意义的装箱套壳,建起来终究是要执行的
甚至
fun<R> lit(:R): ()->R
组合器都能起到和AST同样的效果,OO和FP只是复用参数的一种手段,重点是你对目标树型有没有最常见的心智模型Wikipedia
Higher-order abstract syntax
technique for the representation of abstract syntax trees in languages with variable binders