2月に読んだ本やマンガ
2月の読書メーター
読んだ本の数:15
読んだページ数:2699
ナイス数:0
法華経 2018年4月 (100分 de 名著)
読了日:02月03日 著者:
エイジ’87 1 (1巻) (ヤングキングコミックス)
読了日:02月03日 著者:上山 道郎
武の心 (文春文庫)
読了日:02月07日 著者:津本 陽
甘々と稲妻(12) (アフタヌーンKC)
読了日:02月07日 著者:雨隠 ギド
バキ外伝 疵面-スカーフェイス-(8) (チャンピオンREDコミックス)
読了日:02月08日 著者:板垣恵介,山内雪奈生
フェイト/エクストラ CCC (4) (角川コミックス・エース)
読了日:02月12日 著者:ろび~な
海と陸をつなぐ進化論 気候変動と微生物がもたらした驚きの共進化 (ブルーバックス)
読了日:02月15日 著者:須藤 斎
はぐれアイドル地獄変 (8) (ニチブンコミックス)
読了日:02月19日 著者:高遠 るい
ベタープログラマ ―優れたプログラマになるための38の考え方とテクニック
読了日:02月19日 著者:Pete Goodliffe
3×3EYES 鬼籍の闇の契約者(4) (ヤンマガKCスペシャル)
読了日:02月21日 著者:高田 裕三
入門 監視 ―モダンなモニタリングのためのデザインパターン
読了日:02月22日 著者:Mike Julian
NHK「100分de名著」ブックス道元 正法眼蔵―わからないことがわかるということが悟り
読了日:02月23日 著者:ひろ さちや
オーバーロード (11) (角川コミックス・エース)
読了日:02月26日 著者:深山 フギン,大塩 哲史
オーバーロード 不死者のOh! (4) (角川コミックス・エース)
読了日:02月26日 著者:じゅうあみ
NHK「100分de名著」ブックス 荘子
読了日:02月26日 著者:玄侑 宗久
読書メーター
RubyのRefinementでモジュールincludeやalias定義はどうなるか
確認してみた結果、refine
でinclude
したモジュールのメソッドや定義したエイリアスは、refinementをusing
したときだけ有効になった。
refine
でinclude
したモジュールはusing
しても見えないがメソッドは有効になるようだ。
確認コード:
module IncludeMethod def include_method :include end end module RefineMethod refine Object do include IncludeMethod def refine_method :refine end alias refine_method_alias refine_method end end p Object.include? IncludeMethod begin refine_method rescue p $! end begin refine_method_alias rescue p $! end begin include_method rescue p $! end using RefineMethod p Object.include? IncludeMethod p refine_method p refine_method_alias p include_method
確認結果:
$ ruby ex_refine.rb false #<NameError: undefined local variable or method `refine_method' for main:Object Did you mean? define_method> #<NameError: undefined local variable or method `refine_method_alias' for main:Object Did you mean? define_method> #<NameError: undefined local variable or method `include_method' for main:Object> false :refine :refine :include
Emacs-Lispのリスト用関数
よく知られたmapcar
以外にもリスト操作のための関数がないか探したら、seq-
系の関数が該当するようだ。
(seq-elt sequence index) (seq-length sequence) (seqp sequence) (seq-drop sequence n) (seq-take sequence n) (seq-take-while predicate sequence) (seq-drop-while predicate sequence) (seq-do function sequence) (seq-map function sequence) (seq-map-indexed function sequence) (seq-mapn function &rest sequences) (seq-remove predicate sequence) (seq-reduce function sequence initial-value) (seq-some predicate sequence) (seq-find predicate sequence &optional default) (seq-every-p predicate sequence) (seq-empty-p sequence) (seq-count predicate sequence) (seq-sort function sequence) (seq-sort-by function predicate sequence) (seq-set-equal-p sequence1 sequence2 &optional testfn) (seq-position sequence elt &optional function) (seq-uniq sequence &optional function) (seq-subseq sequence start &optional end) (seq-concatenate type &rest sequences) (seq-mapcat function sequence &optional type) (seq-partition sequence n) (seq-intersection sequence1 sequence2 &optional function) (seq-difference sequence1 sequence2 &optional function) (seq-group-by function sequence) (seq-into sequence type) (seq-min sequence) (seq-max sequence) (seq-doseq (var sequence) body...) (seq-let arguments sequence body...) (seq-random-elt sequence)
たいていのことは出来そうだ。
RubyのRefinementされたメソッドの性能
通常のメソッドと比べて性能に差があるのかどうか比べてみた。
require 'benchmark' class Integer def to_comma to_s.reverse.scan(/\d\d?\d?/).join(',').reverse end end def method_no_args end module RefineMethod refine Object do def refine_method_no_args end end end n = ARGV.shift || '1_000_000' n = n.to_i puts "#{n.to_comma} times." Benchmark.bm(45) do |x| x.report('method_no_args') { n.times do method_no_args end } x.report('refine_method_no_args') { using RefineMethod n.times do refine_method_no_args end } end
結果、まったく差がなかった。
1,000,000 times. user system total real method_no_args 0.549699 0.000000 0.549699 ( 0.550169) refine_method_no_args 0.500810 0.000000 0.500810 ( 0.501193)
性能のことは気にせずRefinementを使おう。
Rubyのaccept_nonblock(exception: false)
Rubyのサーバーソケットのaccept_nonblock
は、IO
のread_nonblock
と同様にexception: false
でIO::WaitReadable
を投げないようにできる。
例外を投げる場合と投げない場合で、どれくらい差があるものなのか実験してみた。
require 'benchmark' require 'socket' class Integer def to_comma to_s.reverse.scan(/\d\d?\d?/).join(',').reverse end end repeat_num = Integer(ARGV.shift || '1_000_000') puts "repeat: #{repeat_num.to_comma}" s = TCPServer.new(0) Benchmark.bm(35) do |x| x.report('accept_nonblock') do repeat_num.times do begin s.accept_nonblock rescue IO::WaitReadable, Errno::EINTR # nothing to do. end end end x.report('accept_nonblock(exception: false)') do repeat_num.times do begin if (r = s.accept_nonblock(exception: false)) then if (r != :wait_readable) then r end end rescue Errno::EINTR # `exception: false'で捕捉されるのは # EAGAIN/EWOULDBLOCK,ECONNABORTE,EPROTOだけなので、例外EINTRの # 捕捉は必要。 end end end end
結果:
$ ./benchmark_socket_accept_nonblock.rb repeat: 1,000,000 user system total real accept_nonblock 20.477151 7.877416 28.354567 ( 29.273192) accept_nonblock(exception: false) 2.606960 6.471008 9.077968 ( 9.108173)
exception: false
の方が3倍速い。
しかし差がつくのはそもそも接続が来ないときなんだよな。
使ったほうがよいのかどうか迷う。