阔以用来查找erlong的库函数的用法:erlong 中文手册
好像if后面的判断条件(guard关卡)不能是函数,case后的就行
-module(lpfmerge).
-export([getstr/1,to_string/1]).
getstr([])->"";
getstr([H|T])->
if
is_atom(H)->[atom_to_list(H)|getstr(T)];
is_integer(H)->[integer_to_list(H)|getstr(T)];
is_float(H)->[float_to_list(H,[{decimals,1}])|getstr(T)]; %注意这里小数点保留一位
is_list(H)->[H|getstr(T)]
end.
to_string(L)->binary_to_list(list_to_binary(getstr(L))).
最后一句就是先转换成 二进制文件 然后再转换回list,不然就会成下面第四个运行代码那样是分开的
PS D:\lpf\lpf练习题\未完成\1> erl
Eshell V8.3 (abort with ^G)
1> c(lpfmerge).
{ok,lpfmerge}
2> L=[1,a,4.9,"sdfds"].
[1,a,4.9,"sdfds"]
3> lpfmerge:to_string(L).
"1a4.9sdfds"
4> lpfmerge:getstr(L).
["1","a","4.9","sdfds"]
5>
先用2个参数的把元组都统一弄成列表 然后再处理
-module(q2).
-export([getPosVal/2]).
getPosVal([],Pos)->[]; %列表为空
getPosVal({},Pos)->{}; %元组为空
getPosVal(L,Pos)->
if
is_tuple(L)->
getPosVal(tuple_to_list(L),Pos); %如果是元组,就先转换成列表
true->
getPosVal(L,Pos,1)
end.
getPosVal([H|T],Pos,Index)when Pos==Index->H;
getPosVal([H|T],Pos,Index)->getPosVal(T,Pos,Index+1).
PS D:\lpf\lpf练习题\已完成\2> erl
Eshell V10.7 (abort with ^G)
1> c(q2).
q2.erl:4: Warning: variable 'Pos' is unused
q2.erl:5: Warning: variable 'Pos' is unused
q2.erl:14: Warning: variable 'T' is unused
q2.erl:15: Warning: variable 'H' is unused
{ok,q2}
2> L=[10,20,30,40,50,60].
[10,20,30,40,50,60]
3> q2:getPosVal(L,3).
30
4>
-module(lpffilter).
-export([filter/1]).
filter([])->[];
filter({})->{};
filter([H|T])->
if
is_tuple(H)
->filter(tuple_to_list(H)); %之前写成 ->filter([tuple_to_list(H)|T]);就不对,为啥喃?
(H rem 2)=:=0
->[H|filter(T)];
true
->filter(T)
end.
PS D:\lpf\lpf练习题\已完成\3> erl
Eshell V8.3 (abort with ^G)
1> c(lpffilter).
{ok,lpffilter}
2> L=[1,2,3,4,5,6,7,8,{9,10,11,12},13,14,15,16].
[1,2,3,4,5,6,7,8,{9,10,11,12},13,14,15,16]
3> lpffilter:filter(L).
[2,4,6,8,10,12]
4>
-module(q4).
-export([filter/2]).
filter(F,[H|T])->
case F(H) of
true->[H|filter(F,T)];
false->filter(F,T)
end;
filter(F,[])->[].
PS D:\lpf\lpf练习题\已完成\4> erl
Eshell V10.7 (abort with ^G)
1> c(q4).
q4.erl:16: Warning: variable 'F' is unused
{ok,q4}
2> L=[1,2,3,4,5,6,7,8].
[1,2,3,4,5,6,7,8]
3> F=fun(X)->(X rem 2) =:=0 end.
#Fun
4> q4:filter(F,L).
[2,4,6,8]
5>
我是写的for循环来做的,计算的是 [ I , J ) [I,J) [I,J) 左闭右开区间的和
用if判断:
-module(lpffor).
-export([for/4]).
for(Index,I,J,[H|T])->
if
(Index>=I) and (Index<J)
->H+for(Index+1,I,J,T);
true
->for(Index+1,I,J,T)
end;
for(Index,I,J,[])->0.
用 when 判断:
-module(lpffor).
-export([for/4]).
for(Index,I,J,[H|T]) when (Index>=I) , (Index<J)
->H+for(Index+1,I,J,T);
for(Index,I,J,[H|T])
->for(Index+1,I,J,T);
for(Index,I,J,[])
->0.
PS D:\lpf\lpf练习题\未完成\5> erl
Eshell V8.3 (abort with ^G)
1> c(lpffor).
lpffor.erl:11: Warning: variable 'I' is unused
lpffor.erl:11: Warning: variable 'Index' is unused
lpffor.erl:11: Warning: variable 'J' is unused
{ok,lpffor}
2> L=[10,20,30,40,50,60,70,80,90].
[10,20,30,40,50,60,70,80,90]
3> lpffor:for(1,2,7,L).
200
4>
这是看的别人的代码,原来export中只写在外面调用的函数就行,里面用到的其他函数可以不写,比如这里用了is_prefix2
还有就是,要想对列表操作的话,参数就要写成,(H|T)这种,这样写的话又不能表示整体的这个列表了,所以这里要弄两个
-module(q6).
-export([is_prefix/2]).
is_prefix([], L2) -> false;
is_prefix([], []) -> false;
is_prefix(L1, L2) ->
if
length(L1) >= length(L2)
-> false;
true
-> is_prefix2(L1,L2)
end.
is_prefix2([H1|T1],[H2|T2]) ->
if
(H1 == H2 andalso T1 == [] )
-> true;
H1 == H2
-> is_prefix2(T1,T2);
H1 /= H2
-> false;
T1 == []
-> true
end.
PS D:\lpf\lpf练习题\未完成\6> erl
Eshell V8.3 (abort with ^G)
1> c(q6).
q6.erl:4: Warning: variable 'L2' is unused
q6.erl:5: Warning: this clause cannot match because a previous clause at line 4 always matches
{ok,q6}
2> L1=[1,2,3].
[1,2,3]
3> L2=[1,2,3,4,5].
[1,2,3,4,5]
4> L3=[2,3,4].
[2,3,4]
5> q6:is_prefix(L1,L2).
true
6>
-module(lpfReverse).
-export([lpfreverse/1,lpfreverse/2]).
lpfreverse(L)->lpfreverse(L,[]).
lpfreverse([H|T],Reversed)->lpfreverse(T,[H|Reversed]);
lpfreverse([],Reversed)->Reversed.
PS D:\lpf\lpf练习题\未完成\7> erl
Eshell V8.3 (abort with ^G)
1> c(lpfReverse).
{ok,lpfReverse}
2> L=[1,3,5,7,9].
[1,3,5,7,9]
3> lpfReverse:lpfreverse(L).
[9,7,5,3,1]
4>
书上的快排例子,erlong写快排好简洁呀ヽ( ̄▽ ̄)ノ
-module(lpfsort).
-export([sort/1]).
sort([])->[];
sort([Mid|T])
->sort([X||X<-T , X<Mid]) ++ [Mid] ++ sort([X||X<-T , X>=Mid]).
-module(q9).
-export([get_sum_rem/2]).
get_sum_rem(L,Num)
->{sum(L)/Num,sum(L) rem Num}.
sum([H|T])->H+sum(T);
sum([])->0.
PS D:\lpf\lpf练习题\未完成\9> erl
Eshell V8.3 (abort with ^G)
1> c(q9).
q9.erl: no such file or directory
error
2> c(q9).
{ok,q9}
3> L=[10,20,30,40,50].
[10,20,30,40,50]
4> q9:get_sum_rem(L,7).
{21.428571428571427,3}
5> 150/7.
21.428571428571427
6>
这个是直接在shell里写
大概就是写一个会产生错误的函数,比如 generate_exception(1),因为看下面错误信息的第一行 shell_undef ,意思是没有定义这个函数
然后就会报错,调用get_stacktrace()就能得到栈的信息了
PS D:\lpf\lpf练习题\未完成\10> erl
Eshell V8.3 (abort with ^G)
1> try generate_exception(1)
catch
error:X->
{X,erlang:get_stacktrace()}
end.
{{shell_undef,generate_exception,1,[]},
[{shell,shell_undef,2,[{file,"shell.erl"},{line,1061}]},
{erl_eval,local_func,6,[{file,"erl_eval.erl"},{line,562}]},
{erl_eval,try_clauses,8,[{file,"erl_eval.erl"},{line,904}]},
{shell,exprs,7,[{file,"shell.erl"},{line,686}]},
{shell,eval_exprs,7,[{file,"shell.erl"},{line,641}]},
{shell,eval_loop,3,[{file,"shell.erl"},{line,626}]}]}
2>
这里是最大值最小值分开的:
-module(lpfMaxMin).
-export([lpfmax/1,lpfmin/1]).
lpfmax([H|T])->lpfmax(T,H). %这里为啥要用. 因为是调用2个参数的lpfmax了,不属于原来的了
lpfmax([],Res)->Res; %只剩一个
lpfmax([H|T],Res)when H>Res->lpfmax(T,H); %比Res大就选他
lpfmax([H|T],Res)->lpfmax(T,Res). %不然不选
lpfmin([H|T])->lpfmin(T,H).
lpfmin([],Res)->Res;
lpfmin([H|T],Res)when H<Res->lpfmin(T,H);
lpfmin([H|T],Res)->lpfmin(T,Res).
PS D:\lpf\lpf练习题\已完成\11> erl
Eshell V8.3 (abort with ^G)
1> c(lpfMaxMin).
lpfMaxMin.erl:8: Warning: variable 'H' is unused
lpfMaxMin.erl:17: Warning: variable 'H' is unused
{ok,lpfMaxMin}
2> L=[5,9,8,7,25,3,2,1].
[5,9,8,7,25,3,2,1]
3> lpfMaxMin:lpfmax(L).
25
4> lpfMaxMin:lpfmin(L).
1
5>
然后是一起返回的写法:
-module(q11).
-export([max_min/1]).
max_min([H|T])->max_min([H|T],H,H). %最开始写成max_min(L)->max_min(L,Max,Min) 会报错说 :variable 'Max' is unbound以及variable 'Min' is unbound
max_min([],Max,Min)->{Max,Min};
max_min([H|T],Max,Min)->
if
(H>Max) and (H<min)
->max_min(T,H,H);
(H>Max)
->max_min(T,H,Min);
(H<Min)
->max_min(T,Max,H);
true
->max_min(T,Max,Min)
end.
PS D:\lpf\lpf练习题\已完成\11> erl
Eshell V8.3 (abort with ^G)
1> c(q11).
q11.erl:4: variable 'Max' is unbound
q11.erl:4: variable 'Min' is unbound
error
2> c(q11).
{ok,q11}
3> L=[5,9,8,7,25,3,2,1].
[5,9,8,7,25,3,2,1]
4> q11:max_min(L).
{25,1}
5>
-module(q12).
-export([get_index/2]).
get_index(L, Tofind) ->get_index(L, Tofind, 1). %调用3个参数的get_index
get_index([],Tofind,Index)->null; %递归边界
get_index([H|T],Tofind,Index)->
if H==Tofind
->Index;
true
->get_index(T,Tofind,Index+1)
end.
PS D:\lpf\lpf练习题\未完成\12> erl
Eshell V8.3 (abort with ^G)
1> c(q12).
q12.erl:6: Warning: variable 'Index' is unused
q12.erl:6: Warning: variable 'Tofind' is unused
{ok,q12}
2> L=[10,20,{33,34,35},40,50].
[10,20,{33,34,35},40,50]
3> q12:get_index(L,{33,34,35}).
3
4>
q12:get_index(L,40).
4
5>
-module(q14).
-export([is_in/2]).
is_in(L1,L2)->is_in(L1,L2,1,1).
is_in([],L2,Index1,Index2)->false;
is_in(L1,[],Index1,Index2)->false;
is_in([H1|T1],[H2|T2],Index1,Index2)->
if
(H1==H2) and (T1==[])
->{true,Index2-Index1+1}; %完全匹配成功
H1==H2
->is_in(T1,T2,Index1+1,Index2+1); %部分匹配成功
true
->is_in([H1|T1],T2,Index1,Index2+1) %没有匹配成功
end.
PS D:\lpf\lpf练习题\未完成\14> erl
Eshell V8.3 (abort with ^G)
1>
c(q14).
q14.erl:6: Warning: variable 'Index1' is unused
q14.erl:6: Warning: variable 'Index2' is unused
q14.erl:6: Warning: variable 'L2' is unused
q14.erl:7: Warning: variable 'Index1' is unused
q14.erl:7: Warning: variable 'Index2' is unused
q14.erl:7: Warning: variable 'L1' is unused
{ok,q14}
2> L1=[3,5,7,3].
[3,5,7,3]
3> L2=[8,3,5,3,5,7,3,9,3,5,6,3].
[8,3,5,3,5,7,3,9,3,5,6,3]
4> q14:is_in(L1,L2).
{true,4}
5> q14:is_in(L2,L1).
false
6>
-module(q15).
-export([lpfsum/1]).
lpfsum(L)->lpfsum(tuple_to_list(L),0,0). %注意输入进来的是元组,还要转换成列表
lpfsum([],Odd,Even)->(Odd/3+Even*3);
lpfsum([H|T],Odd,Even)->
if
(H rem 2)==1
->lpfsum(T,Odd+H,Even);
true
->lpfsum(T,Odd,Even+H)
end.
PS D:\lpf\lpf练习题\未完成\15> erl
Eshell V8.3 (abort with ^G)
1> c(q15).
{ok,q15}
2> L={8,5,2,9,6,4,3,7,1}.
{8,5,2,9,6,4,3,7,1}
3> q15:lpfsum(L).
68.33333333333333
4>
思路还是用的库函数 proplists:append_values 来从L3中找重复的键值
-module(q17).
-export([key_val/3]).
key_val(L1,L2,L3)->key_val(L1,L2,L3,[]).
key_val([],[],L3,Res)->io:format("Res=~w~n",[Res]),Res; %这里不懂为什么,都已经得到最后的答案Res了,但是为啥返回的Res是个奇怪的东西"<61"
key_val([H1|T1],[H2|T2],L3,Res)->
TP1=proplists:append_values(H1,L3), %用库函数从L3中查找这个key并且得到所有的值
TP2=lists:sum(TP1), %返回的是列表,所以要求和
%io:format("TP2=~w~n",[TP2]), %试着打印出来看对不对
key_val(T1,T2,L3,lists:append(Res,[H2+TP2])). %加上L2中的值
不知道为啥会有个奇怪的返回值 “<61”
PS D:\lpf\lpf练习题\未完成\17> erl
Eshell V10.7 (abort with ^G)
1> c(q17).
q17.erl:8: Warning: variable 'L3' is unused
{ok,q17}
2> L1=[a,b,c].
[a,b,c]
3> L2=[10,20,30].
[10,20,30]
4> L3=[{a,23},{b,34},{a,27},{c,78}].
[{a,23},{b,34},{a,27},{c,78}]
5> q17:key_val(L1,L2,L3).
Res=[60,54,108]
"<6l"
6>
哦原来是因为[60,54,108]本身就代表"<6l",可能是某个编码,不信输入进shell试试
PS D:\lpf> erl
Eshell V10.7 (abort with ^G)
1> L=[60,54,108].
"<6l"
2> L.
"<6l"
3>
-module(q18).
-export([select/3,delete/3]).
select(L,N,Key)->select(L,N,Key,1).
select([{K,V}|T],N,Key,Index)->
if
(K==Key) and (Index==N)->
{K,V};
(K==Key)->
select(T,N,Key,Index+1);
true->
select(T,N,Key,Index)
end.
delete(L,N,Key)->delete(L,N,Key,1).
delete([{K,V}|T],N,Key,Index)->
if
(K==Key) and (Index==N)->
T; %找到就返回后面的列表,当前的数不要了
(K==Key)->
[{K,V}|delete(T,N,Key,Index+1)];
true->
[{K,V}|delete(T,N,Key,Index)]
end.
PS D:\lpf\lpf练习题\未完成\18> erl
Eshell V10.7 (abort with ^G)
1> c(q18).
{ok,q18}
2> L=[{a,10},{b,21},{a,10},{b,22},{b,23},{c,30}].
[{a,10},{b,21},{a,10},{b,22},{b,23},{c,30}]
3> q18:select(L,3,b).
{b,23}
4> q18:delete(L,3,b).
[{a,10},{b,21},{a,10},{b,22},{c,30}]
5>
-module(q19).
-export([string_div/2]).
string_div(Str,[X])->string_div(Str,[X],[],[]).
%假如调用函数的时候是:
%string_div("abcabcabc","b")
%此时"abcabcabc"=[97,98,99,97,98,99,97,98,99]
%"b"=[98]
%所以H和X才是同样类型的才能比较
string_div([H|T],[X],Res1,Res2)-> %Res1是保存最后的答案,Res2是保存没有逗号连着的字符串
if H/=X->
string_div(T,[X],Res1,Res2++[H]);
true->
string_div(T,[X],Res1++[Res2],[])
end;
string_div([],[X],Res1,Res2)-> %递归边界
Res1++[Res2].
PS D:\lpf\lpf练习题\未完成\19> erl
Eshell V10.7 (abort with ^G)
1> c(q19).
q19.erl:20: Warning: variable 'X' is unused
{ok,q19}
2> q19:string_div("abcabcabc","b").
["a","ca","ca","c"]
3>
PS D:\lpf\lpf练习题\未完成\19> erl
Eshell V10.7 (abort with ^G)
1>
L1=["ab","c"].
["ab","c"]
2> L2=["de"].
["de"]
3>
[L3]=L2. %把列表L2里的元素取出来,放到L3中
["de"]
4> L3. %L3就不是列表了
"de"
5>
L1++L2. %列表与列表相++,直接会用逗号相隔开
["ab","c","de"]
6>
L1++L3. %由于L3不是列表了,所以看成列表与单个的元素相++
["ab","c",100,101]
7>
看一个列表++不同的数的效果
L1++100
L1++[100]
L1++[[100]]
L1++[[[100]]]
L1=["ab","c"].
["ab","c"]
14>
L1++100.
["ab","c"|100] %++的不是列表,只是单个的元素
15>
L1++[100].
["ab","c",100] %++的是列表,正常操作
16>
L1++[[100]].
["ab","c","d"] %诶~多弄一层括号就变成字符串了
17>
L1++[[[100]]].
["ab","c",["d"]] %再多弄一层就没效果了
20> L1++[100,101].
["ab","c",100,101]
21> L1++[[100,101]]. %这样"d","e"就能连起了
["ab","c","de"]
22> L1++[[100],[101]]. %这样"d","e"就不会连起
["ab","c","d","e"]
在函数中好像又不一样了
Res++H
Res++[H]
Res++[[H]]
这三者的不同之处:
-module(strtest).
-export([str1/1,str2/1,str3/1]).
str1(Str)->str1(Str,[]).
str1([],Res)->Res;
str1([H|T],Res)->
str1(T,Res++H). %H是个元素,不能直接与列表++
%输出结果:
% ** exception error: bad argument
% in operator ++/2
% called as 97 ++ 98
% in call from strtest:str1/2 (strtest.erl, line 7)
str2(Str)->str2(Str,[]).
str2([],Res)->Res;
str2([H|T],Res)->
str2(T,Res++[H]). %[H]就变成了单元素的列表,可以++
%输出结果:"abcde"
str3(Str)->str3(Str,[]).
str3([],Res)->Res;
str3([H|T],Res)->
str3(T,Res++[[H]]). %这。。。。。
%输出结果:["a","b","c","d","e"]
PS D:\lpf\lpf练习题\未完成\19> erl
Eshell V10.7 (abort with ^G)
1> c(strtest).
{ok,strtest}
2> Str="abcde".
"abcde"
3>
strtest:str1(Str).
** exception error: bad argument
in operator ++/2
called as 97 ++ 98
in call from strtest:str1/2 (strtest.erl, line 7)
4>
strtest:str2(Str).
"abcde"
5>
strtest:str3(Str).
["a","b","c","d","e"]
6>
-module(q21).
-export([multiEven/1]).
multiEven(L)->binary_to_list(list_to_binary(multiEven(L,1))). %不转成二进制再转回来的话就会有很多中括号,我也不知道该怎么办
multiEven([],Index)->[];
multiEven([H|T],Index)->
if
(H rem 2)==0
->[H*Index,multiEven(T,Index+1)];
true
->multiEven(T,Index)
end.
PS D:\lpf\lpf练习题\未完成\21> erl
Eshell V8.3 (abort with ^G)
1> c(q21).
q21.erl:6: Warning: variable 'Index' is unused
{ok,q21}
2> L=[5,1,8,7,3,9,2,6,4].
[5,1,8,7,3,9,2,6,4]
3> q21:multiEven(L).
[8,4,18,16]
4>
-module(q22).
-export([sort/1]).
sort(L)->lists:keysort(2,L). %用lists里面的keysort,好像只能升序
PS D:\lpf\lpf练习题\未完成\22> erl
Eshell V8.3 (abort with ^G)
1>
c(q22).
{ok,q22}
2> L=[{"a",5},{"b",1},{"c",8},{"d",7},{"e",3},{"f",9},{"g",2},{"h",6},{"i",4}].
[{"a",5},
{"b",1},
{"c",8},
{"d",7},
{"e",3},
{"f",9},
{"g",2},
{"h",6},
{"i",4}]
3> q22:sort(L).
[{"b",1},
{"g",2},
{"e",3},
{"i",4},
{"a",5},
{"h",6},
{"d",7},
{"c",8},
{"f",9}]
4>
-module(q23).
-export([sumT/1]).
sumT(L)->sum(tuple_to_list(L)). %元组换成列表
sum([])->0;
sum([H|T])->
if
(H rem 2)==1
->H+sum(T);
true
->sum(T)
end.
PS D:\lpf\lpf练习题\未完成\23> erl
Eshell V8.3 (abort with ^G)
1> c(q23).
{ok,q23}
2> L={8,5,2,9,6,4,3,7,1}.
{8,5,2,9,6,4,3,7,1}
3> q23:sumT(L).
25
4>
-module(q24).
-export([find/2,solve1/4,solve2/3,solve3/4,solve/4]).
find(L,Pos)->find(L,Pos,1).
find([H|T],Pos,Index)->
if Pos==Index->
H;
true->
find(T,Pos,Index+1)
end.
solve1(I1,I2,D,L)->solve1(I1,I2,D,L,1). %相等时候的操作
solve1(I1,I2,D,[],Index)->[];
solve1(I1,I2,D,[H|T],Index)->
if Index==I1->
solve1(I1,I2,D,T,Index+1); %把I1位置的删了
Index==I2->
[D,H|solve1(I1,I2,D,T,Index+1)]; %再把D添加到I2位置前面
true->
[H|solve1(I1,I2,D,T,Index+1)]
end.
solve2(V1,I2,L)->solve2(V1,I2,L,1). %不相等时候的操作
solve2(V1,I2,[H|T],Index)->
if Index==I2->
[V1|T];
true->
[H|solve2(V1,I2,T,Index+1)]
end.
solve3(I1,I2,D,L)-> %两个操作合并
V1=find(L,I1),
V2=find(L,I2),
if V1==V2->
solve1(I1,I2,D,L);
true->
solve2(V1,I2,L)
end.
solve(I1,I2,D,L)->list_to_tuple(solve3(I1,I2,D,tuple_to_list(L))). %因为题目要求是元组,所以转换哈
PS D:\lpf\lpf练习题\未完成\24> erl
Eshell V10.7 (abort with ^G)
1> c(q24).
q24.erl:18: Warning: variable 'D' is unused
q24.erl:18: Warning: variable 'I1' is unused
q24.erl:18: Warning: variable 'I2' is unused
q24.erl:18: Warning: variable 'Index' is unused
{ok,q24}
2> L={10,20,30,20,50,60}.
{10,20,30,20,50,60}
3> q24:solve(2,3,7,L).
{10,20,20,20,50,60}
4> q24:solve(2,4,7,L).
{10,30,7,20,50,60}
5>
%lists:keydelete 是删除某一个,这个函数是删除所有的,就是遍历一哈嘛
-module(q25).
-export([key_delete_all/2]).
key_delete_all(L,Key)->key_delete_all(L,Key,L).
key_delete_all([],Key,L)->L;
key_delete_all([{K,V}|T],Key,L)->
if
K==Key->
key_delete_all(T,Key,lists:keydelete(Key,1,L));
true->
key_delete_all(T,Key,L)
end.
PS D:\lpf\lpf练习题\未完成\25> erl
Eshell V10.7 (abort with ^G)
1> c(q25).
q25.erl:6: Warning: variable 'Key' is unused
q25.erl:7: Warning: variable 'V' is unused
{ok,q25}
2> T = [{a, 1}, {b, 2},{b,2}, {c, 3}, {d, 4}].
[{a,1},{b,2},{b,2},{c,3},{d,4}]
3> q25:key_delete_all(T,b).
[{a,1},{c,3},{d,4}]
4>
%这个难道不是直接用库函数 lists:keyreplace 嘛???
-module(q26).
-export([replace_one/2]).
replace_one(L,{K,V})->lists:keyreplace(K,1,L,{K,V}).
PS D:\lpf\lpf练习题\未完成\26> erl
Eshell V10.7 (abort with ^G)
1> c(q26).
{ok,q26}
2> T = [{a, 1}, {b, 2},{b,2}, {c, 3}, {d, 4}].
[{a,1},{b,2},{b,2},{c,3},{d,4}]
3> q26:replace_one(T,{b,99}).
[{a,1},{b,99},{b,2},{c,3},{d,4}]
4>
-module(q27).
-export([insert/3]).
insert(L,Pos,Val)->insert(1,[],L,Pos,Val).
insert(Index,Pre,[H|T],Pos,Val)->
if
Pos==0->
[Val]++[H]++T; %加在最前面
Index==Pos->
Pre++[H]++[Val]++T; %这里H和Val都是一个元素,所以要加中括号表示列表才能使用++操作
true->
insert(Index+1,Pre++[H],T,Pos,Val) %这里的H同样
end.
PS D:\lpf\lpf练习题\未完成\27> erl
Eshell V10.7 (abort with ^G)
1> c(q27).
{ok,q27}
2> L=[1,2,3,4,5].
[1,2,3,4,5]
3> q27:insert(L,0,99).
[99,1,2,3,4,5]
4> q27:insert(L,3,99).
[1,2,3,99,4,5]
5>
-module(q28).
-export([sort/1]).
sort(L) ->sort([], L).
sort(NewList,[]) ->NewList;
sort(NewList, L) ->sort(NewList ++ [lists:min(L)], lists:delete(lists:min(L), L)).%选择最小的放在前面
PS D:\lpf\lpf练习题\未完成\28> erl
Eshell V10.7 (abort with ^G)
1> c(q28).
{ok,q28}
2> L=[6,4,5,7,1,8,2,3,9].
[6,4,5,7,1,8,2,3,9]
3> q28:sort(L).
[1,2,3,4,5,6,7,8,9]
4>
-module(q28).
-export([sort/1]).
sort(L)->for1(L,length(L)).
for1(L,0)->L;
for1(L,N)->for1(for2(L),N-1). %调用N次for2,相当于第一层循环
for2([L])->[L]; %这句就是只有一个元素的时候哇
for2([H1,H2|T])->
if
H1>H2->
[H2|for2([H1|T])];
true->
[H1|for2([H2|T])]
end.
-module(q30).
-export([delete/2]).
delete(L,Pos)->delete(L,Pos,1).
delete([H|T],Pos,Index)->
if
Pos==Index->
T; %这里的T是个列表,如果写成[T],答案就变成[1,2,[4,5,6]],就会多中括号
true->
[H|delete(T,Pos,Index+1)]
end.
PS D:\lpf\lpf练习题\未完成\30> erl
Eshell V10.7 (abort with ^G)
1> c(q30).
{ok,q30}
2> L=[1,2,3,4,5,6].
[1,2,3,4,5,6]
3> q30:delete(L,3).
[1,2,4,5,6]
4>
-module(q31).
-export([reverse/2]).
reverse(L,N)->reverse(L,N,1,[]).
reverse([H|T],N,Index,Res)->
if
Index<N->
[H|reverse(T,N,Index+1,[Res|H])]; %要用中括号括起来,不然前面一节就没了
true->
[H|reverse_all(T)]
end.
reverse_all(L)->reverse_all(L,[]). %这一段是全部翻转的代码
reverse_all([],Res)->Res;
reverse_all([H|T],Res)->
reverse_all(T,[H|Res]).
PS D:\lpf\lpf练习题\未完成\31> erl
Eshell V10.7 (abort with ^G)
1> c(q31).
{ok,q31}
2> L=[1,2,3,4,5,6].
[1,2,3,4,5,6]
3> q31:reverse(L,3).
[1,2,3,6,5,4]
4>
我还以为是匿名函数作为参数传进去呢,原来就说用匿名函数判断一哈而已
话说怎么把匿名函数作为参数传进去呢?只知道lists:map()这个函数阔以接受匿名函数,但是那是库函数啊
-module(q32).
-export([valid_max_min/3]).
valid_max_min([],Min,Max)->true;
valid_max_min([H|T],Min,Max)->
F=fun(X,Min,Max)->(X>=Min) andalso (X=<Max)end,
case F(H,Min,Max) of
false->
false;
true->
valid_max_min(T,Min,Max)
end.
PS D:\lpf\lpf练习题\未完成\32> erl
Eshell V10.7 (abort with ^G)
1> c(q32).
q32.erl:4: Warning: variable 'Max' is unused
q32.erl:4: Warning: variable 'Min' is unused
q32.erl:6: Warning: variable 'Max' shadowed in 'fun'
q32.erl:6: Warning: variable 'Min' shadowed in 'fun'
{ok,q32}
2> L=[1,2,3,4,5,6].
[1,2,3,4,5,6]
3> q32:valid_max_min(L,1,6).
true
4>
q32:valid_max_min(L,2,6).
false
5>
q32:valid_max_min(L,1,5).
false
6>
q32:valid_max_min(L,0,7).
true
7>
为什么case of 换成 if 就说 illegal guard expression
难道是 if 后面不能判断函数???
这个是不用匿名函数的
-module(q32).
-export([valid_max_min/3]).
valid_max_min([],Min,Max)->true;
valid_max_min([H|T],Min,Max)->
if
H<Min->
false;
H>Max->
false;
true->
valid_max_min(T,Min,Max)
end.
%匿名函数为:F=fun(X,Min,Max)->(X>=Min) andalso (X=<Max)end,
-module(qqq32).
-export([valid_max_min/4]).
valid_max_min([],Min,Max,F)->true;
valid_max_min([H|T],Min,Max,F)->
case F(H,Min,Max) of
false->
false;
true->
valid_max_min(T,Min,Max,F)
end.
PS D:\lpf\lpf练习题\已完成\32> erl
Eshell V10.7 (abort with ^G)
1> c(qqq32).
qqq32.erl:4: Warning: variable 'F' is unused
qqq32.erl:4: Warning: variable 'Max' is unused
qqq32.erl:4: Warning: variable 'Min' is unused
{ok,qqq32}
2> L=[1,2,3,4,5,6].
[1,2,3,4,5,6]
3> F=fun(X,Min,Max)->(X>=Min) andalso (X=)end.
#Fun
4> qqq32:valid_max_min(L,1,6,F).
true
5>
qqq32:valid_max_min(L,2,6,F).
false
6>
qqq32:valid_max_min(L,1,5,F).
false
7>
qqq32:valid_max_min(L,0,7,F).
true
8>
用库函数
-module(q33).
-export([max_min/1]).
max_min(L)->[lists:max(L),lists:min(L)].
PS D:\lpf\lpf练习题\未完成\33> erl
Eshell V10.7 (abort with ^G)
1> c(q33).
{ok,q33}
2> q33:max_min([1,2,3,4,5,33,44,55]).
[55,1]
3>
-module(q34).
-export([lpfrand/1]).
lpfrand(N)->lpfrand(N,[]).
lpfrand(0,L)->L;
lpfrand(N,L)->
X=rand:uniform(100),
A=lists:member(X,L),
if
(A==false)
->lpfrand(N-1,lists:append(L,[X])); %如果X不在列表里,就把这个元素加进去
true
->lpfrand(N,L)
end.
PS D:\lpf\lpf练习题\未完成\34> erl
Eshell V10.7 (abort with ^G)
1> c(q34).
{ok,q34}
2> q34:lpfrand(10).
[48,3,98,72,60,33,73,52,44,17]
3>
不重复的随机数有个不好理解的算法:这里是相关博客
-module(q35).
-export([bin/1]).
bin(Number)->{(Number band 16#ffff0000) bsr 16,Number band 16#0000ffff}.
PS D:\lpf\lpf练习题\未完成\35> erl
Eshell V8.3 (abort with ^G)
1> c(q35).
{ok,q35}
2> q35:bin(123456789).
{1883,52501}
3>
-module(q36).
-export([match/2]).
match(L1,L2)->match(L1,L2,1).
match(L1,L2,Index)when Index=<length(L1)->
Len=length(L1),
Pos1=rand:uniform(Len), %产生随机数
X1=lists:nth(Pos1,L1), %从L1中选
Pos2=rand:uniform(Len),
X2=lists:nth(Pos2,L2),
[{X1,X2}|match(L1,L2,Index+1)];
match(L1,L2,Index)->[]. %这句话用来递归结束,必须要,因为上面条件不满足的话就不会返回东西
PS D:\lpf\lpf练习题\未完成\36> erl
Eshell V10.7 (abort with ^G)
1> c(q36).
q36.erl:14: Warning: variable 'Index' is unused
q36.erl:14: Warning: variable 'L1' is unused
q36.erl:14: Warning: variable 'L2' is unused
{ok,q36}
2> L1=[a,b,c].
[a,b,c]
3> L2=[10,20,30].
[10,20,30]
4> q36:match(L1,L2).
[{c,10},{b,20},{c,10}]
5> q36:match(L1,L2).
[{a,10},{c,30},{a,20}]
6> q36:match(L1,L2).
[{c,30},{a,30},{c,10}]
7> q36:match(L1,L2).
[{b,30},{b,10},{c,10}]
8> q36:match(L1,L2).
[{c,10},{b,20},{a,10}]
9>
%思路就是都转换成列表来加
-module(q37).
-export([lpfjoin/1]).
lpfjoin(L)->lpfjoin(L,[],[],[]).
lpfjoin([],Binary,[],[])->list_to_binary(Binary);
lpfjoin([],[],Tuple,[])->list_to_tuple(Tuple);
lpfjoin([],[],[],List)->List;
lpfjoin([H|T],Binary,Tuple,List)->
if
is_binary(H)->
Hb=binary_to_list(H), %转换成list
lpfjoin(T,Binary++[Hb],Tuple,List);
(is_tuple(H))->
Ht=tuple_to_list(H), %转换成list
lpfjoin(T,Binary,Tuple++Ht,List);
true
->lpfjoin(T,Binary,Tuple,List++H) %这里的H以及上面的Hb,Ht都已经是列表了,所以++的时候不用再加中括号
end.
PS D:\lpf\lpf练习题\未完成\37> erl
Eshell V10.7 (abort with ^G)
1> c(q37).
{ok,q37}
2>
B=[<<1,2>>,<<3,4>>].
[<<1,2>>,<<3,4>>]
3> q37:lpfjoin(B).
<<1,2,3,4>>
4>
T=[{a,b},{c}].
[{a,b},{c}]
5> q37:lpfjoin(T).
{a,b,c}
6>
L=[[10],[20]].
["\n",[20]]
7> q37:lpfjoin(L).
[10,20]
8>
%思路就是把key和val分别装入KeyList,ValList,然后再合并
-module(q38).
-export([lpfmix/1]).
lpfmix(L)->lpfmix(L,[],[]).
mix([],[],Res)->Res;
mix([Hk|Tk],[Hv|Tv],Res)->
mix(Tk,Tv,Res++[{Hk,Hv}]). %合并到Res中
lpfmix([],KeyList,ValList)->mix(KeyList,ValList,[]);
lpfmix([{K,V}|T],KeyList,ValList)->
X=lists:member(K,KeyList),
if
X==true->
lpfmix(T,KeyList,ValList); %如果K在KeyList列表里面,就不管
true->
TP1=proplists:append_values(K,T), %KeyList里没有的话,就把所以键值为K的提取出来,返回是个列表
TP2=lists:sum(TP1)+V, %把返回的这个列表求和,并且加上当前K的键值V
lpfmix(T,KeyList++[K],ValList++[TP2]) %然后分别加进去
end.
PS D:\lpf\lpf练习题\未完成\38> erl
Eshell V10.7 (abort with ^G)
1> c(q38).
{ok,q38}
2> L=[{a,1},{b,2},{c,3},{b,4},{b,5},{c,6},{d,7},{d,8}].
[{a,1},{b,2},{c,3},{b,4},{b,5},{c,6},{d,7},{d,8}]
3> q38:lpfmix(L).
[{a,1},{b,11},{c,9},{d,15}]
4>
按道理来说这样应该是对的,
-module(q39).
-export([count_characters/1]).
count_characters(Str)->count_characters(Str,#{}).
count_characters([], X) ->X;
count_characters([H|T], #{H=>N}=X) ->
count_characters(T,X#{H:=N+1}); %如果匹配上了,就说明有,就要把N更新成N+1
count_characters([H|T],X)->
count_characters(T,X#{H=>1}). %不然就增加这个映射
但是我的映射不能模式匹配,也就是说会出现下面这种情况,说不合法的匹配 (illegal pattern)
PS D:\lpf\lpf练习题\未完成\39> erl
Eshell V10.7 (abort with ^G)
1> M1=#{a=>10,b=>20}.
#{a => 10,b => 20}
2> #{a=>X}=M1.
* 1: illegal pattern
3>
然后看其他童鞋写的并没有用模式匹配这种方法,用的是maps里的函数
-module(q39).
-export([count_characters/1]).
count_characters(Str)->count_characters(Str,#{}).
count_characters([], M) ->M;
count_characters([H|T], M) ->
case maps:is_key(H,M)of %看H是不是M中的key
false ->
count_characters(T, maps:put(H,1,M)); %如果不是,就在M中增加 H=>1 一个映射
true ->
Count = maps:get(H,M), %获得当前的映射的val
count_characters(T, maps:update(H,Count+1,M)) % H=>Count 这个 映射更新成 H=>Count+1
end.
PS D:\lpf\lpf练习题\未完成\39> erl
Eshell V10.7 (abort with ^G)
1> c(q39).
{ok,q39}
2> q39:count_characters("hello").
#{101 => 1,104 => 1,108 => 2,111 => 1}
3>