特别感谢 peg.js (提供语法解析支持)和 decimal.js (提供高精支持)
- (我是更新区,这里经常变)
- 目前加入了节点链接功能,可以稍微方便点地查看数据流。
- 然后加入了奇怪的 hover 高亮和变量名标注
各位大神一起来把 flea-compiler 黑掉吧!谢谢啦!
(话说是不是出成 uoj 题就会有一堆人来找 bug 来 hack 了 2333)
另外跪求 sigmoid 的靠谱计算方法。。。
众所周知,NOI 2016 旷野大计算,vfk 提供的题解里面,代码是写成这样的
x = in()
p = s((x + 1e-30) << 500) << 152
y = s((x >> 150) + p)
r = x + ((-y + 0.5) << 153) + p
out(r)
于是我就开了个坑,写了个编译器
语法稍微有点变动的说:
{ 我是注释 }
x = in(1) { 1 代表第一个输入 }
p = s((x + 1e-30) << 500) << 152
y = s((x >> 150) + p)
r = x + ((-y + 0.5) << 153) + p
out(r)
可是为什么会这样改呢?因为。。我觉得 I
全在前面没有问题啊。。
那为什么 O
不要都在后面呢。。
这个。。哎呀。。 不要在意那些细节。。
于是生成的代码是
I
C 1 0.000000000000000000000000000001
< 2 500
S 3
< 4 152
> 1 150
+ 6 5
S 7
- 8
C 9 0.5
< 10 153
+ 1 11
+ 12 5
O 13
表达式的语法大家自己体会体会吧 orz,网页上也有一个 help
(话说可以改进呢,泥萌如果想要的话我可以搞几个优先级不一样的 shl
shr
cmp
max
之类的保留字运算符出来啊,大家有意可以在下面讨论)
后来的变量会隐藏前面的变量,所以排序那题就不用生成一大堆临时名字了
写完之后点那个 [Share your fleas]
然后地址栏里就是一个自带代码的网址了,然后就可以 Share 了。哎呀好像有点长。。
然后目前有两个优化:
如果整个子表达式或者整个变量就是个常数,它会被尽量内联,同时造成精度损失(额)。如果真的需要常量节点的话,这么算:$C = (\texttt{in(1)} \gg 10000) + C$
(以下是一点题外话)
$ cat compute.out I > 1 10000 O 2 $ ./checker -f compute.out 1 0.000000000000000000000000000000000000000000000000000000000000000000000000000000000000000001
但是 $2^{-10000} \approx 5.0124\times 10^{-3011}$
公用子表达式消除!Common sub-expression elimination, CSE。发现重复出现的表达式可以避免重复计算。
具体可以见默认的样例代码。
文件的话有这些
http://dram.cf/flea-compiler/
vendor/decimal.min.js
index.html
parse.pegjs
parse.js
由parse.pegjs
生成compiler.js