Erlang代码性能分析

0、内置函数和运算符的性能
1)、++运算符
不要放任列表自右侧增长!此外还应该注意++运算符只是lists:append/2的一个别名,这个问题对该函数同样适用。
2)、- -运算符
- -运算符是lists:substract/2 的别名。这个运算符不常用:它的作用是从左侧列表中删除右侧列表中的元素。
如果元素顺序不是很重要,那么更为高效的方法是先排序,再调用ordersets:substract/2 。
3)、list _to_atom/1
切记原子无法垃圾回收,务必小心使用这个函数。在某些场合使用list _to_existing_atom/1更合适。
4)、length/1
为了计算元素数目,length/1必须遍历整张列表,在特殊场合可以使用模式匹配来代替此函数。
5)、size/1
length/1仅适用于列表,size/1同时适用于元组和二进制串,不适用于列表。
二者的主要区别在于size/1是常数操作,无需遍历所有数据元素。size/1用于元组返回元组的元素个数,用于二进制串返回的是字节数。
推荐使用tuple_size (T)获取元组的元素数,
用byte_size(B)或bit_szie(B)获取二进制串或位串中的字节数或比特位数。

1、用cprof计算调用次数

cprof用于记录函数调用次数。输出信息不如fprof丰富,相对于fprof,主要优势在于对运行时系统的影响较小(被分析的代码大约会慢10%)。因此,如果要对线上运行着的代码进行性能分析,使用cprof更合适。

用做性能分析的代码:

-module(profile_ex).

%% API
-export([run/0]).

run() ->
    spawn(fun() -> looper(1000) end),
    spawn(fun() -> funner(1000) end).

looper(0) ->
    ok;
looper(N) ->
    _ = integer_to_list(N),
    looper(N - 1).

funner(N) ->
    funner(fun(X) -> integer_to_list(X) end, N).

funner(_Fun, 0)->
    ok;
funner(Fun, N)->
    Fun(N),
    funner(Fun, N - 1).


以下Erlang shell会话演示了如何使用cprof来测评上述示例模块的性能。

23> cprof:start().           
8289
24> profile_ex:run().        
<0.82.0>
25> cprof:pause().           
8289
26> cprof:analyse(profile_ex).
{profile_ex,3006,
            [{{profile_ex,looper,1},1001},
             {{profile_ex,funner,2},1001},
             {{profile_ex,'-funner/1-fun-0-',1},1000},
             {{profile_ex,run,0},1},
             {{profile_ex,funner,1},1},
             {{profile_ex,'-run/0-fun-1-',0},1},
             {{profile_ex,'-run/0-fun-0-',0},1}]}
27> cprof:stop().             
8289
28> 

调用cprof:start()后,所有模块的函数调用都将被计数。cprof适用于任何系统,而且不会对运行中的应用产生干扰,因此特别有用。
如果只对特定模块中的函数调用次数产生兴趣,例如,可以通过 cprof:analyse(profile_ex)调用可以单独测试profile_ex模块的性能。

 cprof:pause().令cprof暂停,停止对函数调用进行计数。只需调用cprof:analyse(profile_ex),便可获取prof_ex模块中所有函数的调用次数。

扫描二维码关注公众号,回复: 3772731 查看本文章


2、用fprof测定执行时间

fprof运行时的开销比cprof要大得多,会将代码的运行速度拖慢10倍以上。fprof依赖于runtime_tools应用中的dbg。

以下会话展示了如何使用fprof来分析prof_ex模块:

50> c(profile_ex).                       
{ok,profile_ex}
51> fprof:trace(start). 开始跟踪。 跟踪信息默认写入名为fprof.trace的文件,该文件是二进制模式,不适合阅读。                
ok
52> profile_ex:run().                    
<0.155.0>
53> fprof:trace(stop).                   
ok
54> fprof:profile().  处理跟踪过程。 讲跟踪信息转换为供性能评测用的原始数据,转换后的数据有fprof服务器保存在内存中。                 
Reading trace data...
.............
End of trace!
ok
55> fprof:analyse({dest, "profile.txt"}). 分析性能分析数据。分析数据,将分析结果输出至制定的文件(
profile.txt
 
 
Processing data...
Creating output...
Done!ok
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

猜你喜欢

转载自blog.csdn.net/wangyangkobe/article/details/8973704