用 Ruby 求定积分
纯属无聊……
曾经以为求积分之类的是个很复杂的过程,对那些可以求出积分值的计算程序佩服不以,昨日脑子不知道为什么忽然想到这个问题,翻了翻书,发现这个问题很简单~
用最简单的矩形法,Ruby 代码如下:
-
def integral(a, b, n = 100)
-
sum = 0.0
-
dx = (b - a)/n.to_f
-
n.times do
-
a += dx
-
sum = sum + (yield a)*dx
-
end
-
sum
-
end
n 为精度,Ruby 的 block 真方便,如果要求:
那么就是:
-
integral(0, 1) {|x| x**2 - x**3}
如果要求:
那么就是:
-
integral(0, Math::PI) {|x| Math.sin(x)}
如果函数很复杂,也可以在外面定义一个 f(x),然后写成 integral(a, b) {|x| f(x)},相当美观~
看看结果:
-
puts integral(0, Math::PI) {|x| Math.sin(x)}
-
>> 1.99983550388745
的准确值是 2,看来精度还不错~
嗯嗯……其实本文的真正意义在于,很久很久之前给 is-Programmer 实现了插入 TeX 公式的功能,这是我第一次用上……
用 File.expand_path 过滤文件名
一些情况下,要从用户哪里得到文件名或者目录名参数,比如文件读取、上传、删除,创建目录,还有 typo 那个 theme_controller 中的 css 和 js 缓存。
恶意用户可以输入含有 "../.." 这样的字符的参数,从而跳转到上级目录,读取或者删除一些其他目录的文件,所以必须要过滤,比如 typo 的 theme_controller.rb 代码中:
-
def render_theme_item(type, file, mime = nil)
-
...
-
if file.split(%r{[\\/]}).include?("..")
-
return (render :text => "Not Found", :status => 404)
-
end
-
...
file 来自 params[:filename],检查 file 中是否含有 "..",如果有的话,就不做任何动作返回 404。
但是这样并不能解决所有的问题,参数可以被 URI 编码成 %xx%xx 的形式,而且天知道还有什么字符可以跳转到上级目录 。
最近在看 《Adcanced Rails》这书,上面写了种不错的方法:
-
name = params[:filename]
-
-
base_path = File.expand_path(File.join(RAILS_ROOT, "public"))
-
file_path = File.join(base_path, name)
-
-
if File.expand_path(file_path).start_with?(base_path)
-
data = File.read(file_path)
-
else
-
raise "Access denied"
-
end
File.expand_path 这方法可以扩展路径字符中所有的特殊字符,包括 "~", "..", ".",形成平坦的路径字符串( 原来我一直以为 File.join 也有这个功效…… ),最后只要检查一下文件的最终地址,开头是否为安全的目录即可,这样就可以轻松的将用户的读取范围限制在 base_path 之下了~
编译原理,再开~
看完了《形式语言与自动机导论》,虽然后面的章节明显没有前面看得认真 ,但是对形式语言这块算是有了个总体的认识,DFA、正则表达式、Context-Free Languages、图灵机这些东西之间有什么关系,顿时清楚了很多~
当初看得屁滚尿流败下阵来的《编译原理》,也准备再开,虽然还是没有信心能看完,但是应该比上次好得多 。
伟大的编译器之神,保佑我吧~~
Chito 1.0.6 上传完毕
最近比较折腾,拖了很久,幸运的是修正了在 is-Programmer 使用期间发现的 bug ,更新内容可以参考这里。
自写 html 闭合的一个 Bug
前阵子拿自己写的那个 html 闭合函数,洋洋得意的替换掉了 RubyfulSoup 那个大库,结果却没有发现隐藏在其中的一个 Bug。
当初虽然找了不少 html 样本进行测试,最后却忘记测试 self-close 标签存在的情况,多亏了 獨立的圓 帮我找出了这个问题 。
Bug 就是如果 html 中有 <br/> <img ... /> 这样的标签,闭合函数就会错误的再追加 </br> </img> 这样的标签在简介末尾,要不是导致 獨立的圓 的 Blog 格式混乱,不知道什么时候才能发现这个问题。
知道了问题所在,修正就很简单了,下面就是改善过的版本,不知道还有没有没有考虑到的地方,高亮部分是改动的部分:
-
def close_html(html)
-
stream = html.scan( /<\s*[\/]*[^>^\/]+>/ ).map { |x| x[ /<\s*([^>^\s]* )[^>]*>/, 1]}
-
stack = []
-
stream.each do |x|
-
if x =~ /^\//
-
stack.pop if x[1..-1] == stack.last
-
else
-
stack.push x
-
end
-
end
-
stack.reverse.each {|x| html << "</#{x}>\n"}
-
html
-
end