主题:erlang静态数据查询方式的一种构想 http://www.javaeye.com/topic/461367
解决这个问题有2种方式:
1. 函数匹配
2. per module constant pool
针对这个问题我做了个试验, 构建一个atom->int的查询。
yu-fengdemacbook-2:~ yufeng$ cat t.erl
-module(t).
-export([start/1, start/2]).
start([A1, A2])->
start(list_to_integer(atom_to_list(A1)), A2).
start(N, Meth)->
Start = erlang:now(),
dotimes(N, case Meth of m->fun dict_lookup/1; f->fun fun_lookup/1 end),
Stop = erlang:now(),
erlang:display( N / time_diff(Start, Stop)).
dotimes(0, _) ->
done;
dotimes(N, F) ->
F(N),
dotimes(N - 1, F).
time_diff({A1,A2,A3}, {B1,B2,B3}) ->
(B1 - A1) * 1000000 + (B2 - A2) + (B3 - A3) / 1000000.0 .
dict_lookup(I) ->
{ok, I} = dict:find(list_to_atom("x" ++ integer_to_list(I)), h1:get_dict()) .
fun_lookup(I) ->
I = h2:lookup(list_to_atom("x" ++ integer_to_list(I))).
yu-fengdemacbook-2:~ yufeng$ cat make_dict
#!/opt/local/bin/escript
main([A])->
N = list_to_integer(A),
L = [{list_to_atom("x" ++ integer_to_list(X)), X} || X<-lists:seq(1, N)],
D = dict:from_list(L),
io:format("-module(h1).~n-export([get_dict/0]).~nget_dict()->~n",[]),
erlang:display(D),
io:format(".~n"),
ok.
yu-fengdemacbook-2:~ yufeng$ cat make_fun
#!/opt/local/bin/escript
main([A])->
N = list_to_integer(A),
io:format("-module(h2).~n-export([lookup/1]).~n",[]),
[io:format("lookup(~p)->~p;~n",[list_to_atom("x" ++ integer_to_list(X)), X]) || X<-lists:seq(1, N)],
io:format("lookup(_)->err.~n", []),
ok.
yu-fengdemacbook-2:~ yufeng$ head h1.erl
-module(h1).
-export([get_dict/0]).
get_dict()->
{dict,100,20,32,16,100,60,{[],[],[],[],[],[],[],[],[],[],[],[],[],[],[],[]},{{[[x10|10],[x30|30],[x50|50],[x70|70],[x90|90]],[[x11|11],[x31|31],[x51|51],[x71|71],[x91|91]],[[x12|12],[x32|32],[x52|52],[x72|72],[x92|92]],[[x13|13],[x33|33],[x53|53],[x73|73],[x93|93]],[[x4|4],[x14|14],[x24|24],[x34|34],[x44|44],[x54|54],[x64|64],[x74|74],[x84|84],[x94|94]],[[x5|5],[x15|15],[x25|25],[x35|35],[x45|45],[x55|55],[x65|65],[x75|75],[x85|85],[x95|95]],[[x6|6],[x16|16],[x26|26],[x36|36],[x46|46],[x56|56],[x66|66],[x76|76],[x86|86],[x96|96]],[[x7|7],[x17|17],[x27|27],[x37|37],[x47|47],[x57|57],[x67|67],[x77|77],[x87|87],[x97|97]],[[x8|8],[x18|18],[x28|28],[x38|38],[x48|48],[x58|58],[x68|68],[x78|78],[x88|88],[x98|98]],[[x9|9],[x19|19],[x29|29],[x39|39],[x49|49],[x59|59],[x69|69],[x79|79],[x89|89],[x99|99]],[],[],[],[],[],[]},{[[x20|20],[x40|40],[x60|60],[x80|80],[x100|100]],[[x1|1],[x21|21],[x41|41],[x61|61],[x81|81]],[[x2|2],[x22|22],[x42|42],[x62|62],[x82|82]],[[x3|3],[x23|23],[x43|43],[x63|63],[x83|83]],[],[],[],[],[],[],[],[],[],[],[],[]}}}
.
yu-fengdemacbook-2:~ yufeng$ head h2.erl
-module(h2).
-export([lookup/1]).
lookup(x1)->1;
lookup(x2)->2;
lookup(x3)->3;
lookup(x4)->4;
lookup(x5)->5;
lookup(x6)->6;
lookup(x7)->7;
lookup(x8)->8;
yu-fengdemacbook-2:~ yufeng$ cat test.sh
#!/bin/bash
#OPT=+native
OPT=
echo "build $1..."
echo "make h1..."
./make_dict $1 >h1.erl
echo "make h2..."
./make_fun $1 >h2.erl
echo "compile h1..."
erlc $OPT h1.erl
echo "compile h2..."
erlc $OPT h2.erl
echo "compile t..."
erlc $OPT t.erl
echo "running..."
echo "map..."
erl -s t start $1 m -noshell -s erlang halt
echo "fun..."
erl -s t start $1 f -noshell -s erlang halt
yu-fengdemacbook-2:~ yufeng$ ./test.sh 10000
build 10000...
make h1...
make h2...
compile h1...
compile h2...
compile t...
running...
map...
2.767323e+05
fun...
2.656819e+05
done.
在10000条记录的情况下 每个查询几个us, 速度不是很快.
结果发现 函数和constant pool在处理上上差不多快的。在实践中根据需要采用把。
Recent Comments