array
array由[n]定义,n标示array长度,type是类型。
var arr [10]int
arr[0] = 42
arr[1] = 13
当向函数内传递一个数组的时候,会获得一个数组的副本,而不是数组的指针。
声明数组时,必须在方括号内输入一些内容:数字或者三个点。三个点,go会自动统计元素个数。
a:= [2][2]int{[2]int{1,2},[2]int{3,4}}
a:= [2][2]int{[...]int{1,2},[...]int{3,4}}
或者
a:= [2][2]int{{1,2},{3,4}}//当元素复合声明的类型和外部一致时
slice
slice与数组区别,slice可以怎讲啊长度,slice总是指向底层的一个array。slice是指向array的指针。slice是引用类型的,当一个函数需要一个slice参数,函数内对slice修改。slice总是与一个固定长度的array承兑出现。
int:var array[m]int //创建一个m个元素的array。
slice := array[0:n]
几个长度
len(slice)==n
cap(slice)==m
len(array)==cap(array)==m
map
定义map的方法:map[]
monthdays := map[string]int{
"Jan":31,"Feb":28,
}
最后一个逗号是必须的。
先写到这里了,准备粗略把教程看完。原因是现在用golang学习语法时,太麻烦了。每次都是修改源文件--打开shell--go run,感觉要受不了了,决定写一个像python在shell里一样方便的东西学习语法。
Read more...
Archive for 算法-编程
golang学习-变量和类型
放在同一行的多个语句,必须用分号分隔。
变量的类型在变量名后面。
var a int
var b bool
a = 15
b = false
等价:
a := 15
b := false
多个var声明可以成组。
var{
x int
b bool
}
同样适用于const和import。
相同类型的多个变量可以在一行内完成声明:
a,b := 20,16
一个特殊的变量名_(下划线),任何赋值给他的值都被丢弃。
_,b := 34,35
golang编译器对声明却未使用的变量报错。
变量名 declared and not used。
布尔类型: true和false
数字类型: int ,根据硬件决定长度。32位硬件是32位,64位为64.也可以明确其长度,完整的整数类型表;
int8,int16,int32,int64 byte, uint8,uint16,uint32 uint64.byte是uint8的别名。
浮点型有float32,float64(没有float类型)。
64位的整数和浮点数都是64位的,即便是在32位的架构上。这些类型全部独立,混合这些类型向变量赋值引起编译器错误。
常量:只能是数字、字符串和布尔值。可以使用iota生成枚举值。
const(
a = iota
b = iota
)
第一个iota表示0,因此a为0,当iota再次进行新的一行使用时,值增加1,b的值为1.
可以省略重复的iota。
const(
a = iota
b
)
字符串: string
s := "hello world!"
go中字符串是UTF-8的由双引号包裹。单引号表示一个字符,不是string。一旦给变量赋值,字符串就不能修改了。
一下做法非法:
var s string = "hello"
s[0] = 'c'
go中实现的方法:
Read more...
s := "hello"
c := []byte(s) //转换s为字节数组
c[0] = 'c' //修改数组
s2 := string(c) //创建新字符串
多行字符串
//错误写法:
s := "starting part"
+ "ending part"
//会被转换成
s := "starting part";
+ "ending part";
//正确写法
s := "starting part" +
"ending part"
//另一种写法,使用`反引号作为原始字符串符号
s := `starting part
ending part`
//最后一个s将包含换行。在原始字符串标识中的值字符是不转义的。
//可以写一个例子,将上面修改为:
s := `starting \n part
ending part`
fmt.Printf("%s",s)
//会发现starting和part间没有换行而是‘\n’
rune :int32别名。用UTF-8进行编码。需要遍历字符串中的字符。可以循环每个字符。
复数:变量类型是complex128(64位虚数部分),complex64(32位虚数部分)
复数写为re+imi,re是实数部分,im虚数部分。
var c complex64 = 5+5i
错误:error。var a error定义a为一个error,a的值为int。
golang在windows安装,vim配置,helloworld笔记
安装过程很简单,官网有详细文档:http://golang.org/doc/install#windows
前几天还记得可以访问,今天不行了。汗,我直接下载的zip file 解压到c盘,将c:\go\bin添加到系统变量中,安装完成了。。。
下面说说vim的golang配置,下载地址:https://github.com/jnwhiteh/vim-golang,在直接拖到Vim\vimfiles,搞定。官方给的应该和这个一样,没看,http://golang.org/misc/。
上hello world代码:没高亮(决定改掉他)
Read more...
package main
import "fmt"
func main(){
fmt.Printf("hello world~")
}
编译:go build hello.go
运行: hello
花了五六分钟将插件修改了一下,半支持golang了。golang语法和C比较相似,直接用C的文件修改的,主要修改了一下关键字什么的。现在对golang还不熟悉,没有随便修改。以后发现不正确慢慢修改吧。
当时安装代码高亮插件时,不知道这个东西是在插入数据库的时候修改了文章内容,现在想脱离也必须开着这个插件。想想还是这样吧,插件不更新自己慢慢修改着,反正其他插件也不一定支持,也要修改,只是可能是js实现的
erlang学习笔记--并发编程
erlang被称作纯粹的消息传递语言。在erlang中,和进程打交道只需要3个原语:spawn、 send和receive。
1.关于erlang并发编程的一个例子。
先上代码:
[caption id="attachment_618" align="alignnone" width="300" caption="erlang并发编程"]
[/caption]
20> c(area_server1.erl).
{ok,area_server1}
21> Pid3 = area_server1:start().
<0.98.0>
22> area_server1:area(Pid3,{rectangle,10,10}).
100
<0.40.0>
代码分析:
第四行,来自并发原语Pid = spawn(Fun),创建一个新进程,对Fun求值。新进程与调用者所在的进程并发运行。spawn返回一个Pid。
第八行,并发原语Pid ! Message,想进程标识符为Pid的进程发送消息。消息发送是异步的,发送者无需等待返回结果就可继续处理自己的事务。
receive ... end 接受一个发给当前进程的消息,进行匹配,如果没有匹配到,消息会留给后续过程来处理,然后进程等待下一条消息。
当输入命令Pid3 = area_server1:start(),创建一个服务端进程。进程执行loop()函数,等待接受消息。
area_server1:area(Pid3,{rectangle,10,10}).输入命令后,将创建一个新进程(客户端进程),到代码第九行,给Pid3发送一条消息,{该客户进程id,{rectangle,10,10}}。然后等待消息返回,等待消息中,匹配模式{Pid,Response}绑定了Pid(这里是Pid3),因为receive...end里只有个匹配模式,所以只有当接受的消息为Pid时,后面的式子才会执行。
给Pid3发送消息后,17-20执行,From为客户端进程id,然后18行像客户端进程发送消息。self()现在为服务端的id,也就是Pid3。然后继续等待消息。
客户端接受消息,11行进行匹配,发现Pid正确,执行后面语句,打印self()(客户端id)。
晚上用零碎时间又修改了一下代码,方便调试。ps:这个代码开始没看懂,借助群里大牛点通了。
[caption id="attachment_620" align="alignnone" width="300" caption="erlang编程2"]
[/caption]
Read more...
[/caption]
20> c(area_server1.erl).
{ok,area_server1}
21> Pid3 = area_server1:start().
<0.98.0>
22> area_server1:area(Pid3,{rectangle,10,10}).
100
<0.40.0>
代码分析:
第四行,来自并发原语Pid = spawn(Fun),创建一个新进程,对Fun求值。新进程与调用者所在的进程并发运行。spawn返回一个Pid。
第八行,并发原语Pid ! Message,想进程标识符为Pid的进程发送消息。消息发送是异步的,发送者无需等待返回结果就可继续处理自己的事务。
receive ... end 接受一个发给当前进程的消息,进行匹配,如果没有匹配到,消息会留给后续过程来处理,然后进程等待下一条消息。
当输入命令Pid3 = area_server1:start(),创建一个服务端进程。进程执行loop()函数,等待接受消息。
area_server1:area(Pid3,{rectangle,10,10}).输入命令后,将创建一个新进程(客户端进程),到代码第九行,给Pid3发送一条消息,{该客户进程id,{rectangle,10,10}}。然后等待消息返回,等待消息中,匹配模式{Pid,Response}绑定了Pid(这里是Pid3),因为receive...end里只有个匹配模式,所以只有当接受的消息为Pid时,后面的式子才会执行。
给Pid3发送消息后,17-20执行,From为客户端进程id,然后18行像客户端进程发送消息。self()现在为服务端的id,也就是Pid3。然后继续等待消息。
客户端接受消息,11行进行匹配,发现Pid正确,执行后面语句,打印self()(客户端id)。
晚上用零碎时间又修改了一下代码,方便调试。ps:这个代码开始没看懂,借助群里大牛点通了。
[caption id="attachment_620" align="alignnone" width="300" caption="erlang编程2"]
[/caption]
利用pil,cStringIO将图片暂存上传
很简单的代码,记录一下。
Read more...
import Image
image = Image.open('a.jpg')
import cStringIO
buf = cStringIO.StringIO()
image.save(buf, image.format,quality=75)
data = buf.getvalue()
a = u.writeFile('/this/logo.jpg',data,True)
应用在 使用django,用户上传图片后,将图片转存到别的服务器。但是转存需要对图片进行处理,但是quality设定的保存,不知道可不可以在不是image.save()的时候。写的这个是保存时放到内存,然后直接提交到图片服务器。
erlang学习笔记--BIF,二进制数据,比特语法
1.BIF:
BIF:(built-in function)内建函数,是erlang语言的组成部分。是erlang虚拟机中的基本操作。
tuple_to_list/1将元组转换为列表,time/0返回当前时间的时,分,秒。
1> tuple_to_list({12,cat,"ddd"}).
[12,cat,"ddd"]
3> time().
{12,35,57}
2.二进制数据:
一种数据类型,用来实现原始数据的高速存储。节省内存,输入输出更加高效。书写打印时,二进制数据以一个整数或者字符序列的形式出现,两端分别用尖括号括起来。其中的整数,每一个都要在0-255之间,如果二进制数据是可以打印的字符串,shell将显示字符串形式,否则会显示一串整数。
@spec 描述函数的参数和返回类型。类型标注,不是erlang代码而是注释文档的一部分,shell中不能使用这些标注。erlang中的模块声明也是注释的一部分。
erlang通过BIF来构造二进制数据或者从中提取数据,或者通过比特语法来完成这一过程。
@spec list_tbo_inary(IoList) -> binary()
@spec split_binary(Bin,Pos) -> {Bin1,Bin2}
@spec term_to_binary(Term) -> Bin
@spec binary_to_term(Bin) -> Term
list_tbo_inary将IoList中所有东西转换为一个二进制数据。split_binary在pos位置将二进制数据分割成两个部分。下面两个是互逆。
4> Bin1 = <<1,2,3>>.
<<1,2,3>>
5> Bin2 = <<4,5>>.
<<4,5>>
6> Bin3 = <<6>>.
<<6>>
7> list_to_binary([Bin1,1,[2,3,Bin2],4|Bin3]).
<<1,2,3,1,2,3,4,5,4,6>>
12> split_binary(<<1,2,3,1,2,3,4,5,4,6>>,4).
{<<1,2,3,1>>,<<2,3,4,5,4,6>>
14> term_to_binary({11,'333a',use}).
<<131,104,3,97,11,100,0,4,51,51,51,97,100,0,3,117,115,101>>
15> binary_to_term(<<131,104,3,97,11,100,0,4,51,51,51,97,100,0,3,117,115,101>>).
{11,'333a',use}
返回二进制数据字节长度
16> size(<<1,2,3,4>>).
4
3.比特语法
比特语法:一种模式匹配语法,用于二进制数据中的比特进行封包和解包工作。
比特语法是模式匹配的一种扩展。编写底层代码时,常会需要对比特级别的二进制数据进行封包解包,会体现比特语法的便捷,比特语法针对协议编程而设计(erlang的看家本领 哇塞)。
16bit色彩的封包解包
19> Red = 2.
2
20> Green = 54.
54
21> Blue = 20.
20
22> Men = <<Red:5,Green:6,Blue:5>>.
<<22,212>>
23> Mem = <<Red:5,Green:5,Blue:5>>.
<<21,84:7>>
24> <<R1:5,G1:6,B1:5>> = Men.
<<22,212>>
25> R1.
2
27> G1.
54
28> B1.
20
可以看到是用:进行匹配,冒号前是数据,后是所占的比特数。
比特语法表达式
嗯,这里讲比特语法格式:
比特语法的形式:<<>>或者<<E1,E2,E3,E4,...,En>>。Ei有四种形式:
Ei = Value | Value:Size | Value/TypeSpecifierList | Value:Size/TypeSpecifierList
二进制数据中总比特数恰好被8整除(二进制数据中每个字节都是8bit)。Value必须是一个绑定变量、文本串或者一个返回值的整数。浮点数、二进制数据的表达式。Size必须为一个整型或者整型绑定变量,不能是自由变量。整型默认Size为8,浮点型为64,二进制则为本身长度。SpecifierList决定字节序,取值为:
@type End = big| little |native
书上给出一个例子来了解这三种排序和默认排序,不同机器可能不同。
37> {<<16#12345678:32/big>>,<<16#12345678:32/little>>,<<16#12345678:32/native>>,<<16#12345678:32>>}.
{<<18,52,86,120>>,
<<120,86,52,18>>,
<<120,86,52,18>>,
<<18,52,86,120>>}
4.使用总结
块表达式:
begin
Expr1,
....
Exprn
end
块得值就是快中最后一个表达式的值,用于当代码某处只允许使用单个表达式而你要用一串表达式时。
注释:
只有行注释%,没有块注释。
列表操作符++ ——:对列表进行添加和删除的中缀操作符。
比较表达式:
所有类型都定义了大小比较顺序:
number<atom<reference<fun<port<pid<tuple<list<binary
作用:可以对存储了任何类型的列表进行排序,并根据比较顺序,编写高效的数据访问代码。
出了=:=,=/=外,其他都遵循下面规则:
如果一个比较参数为整数,另一个浮点数, 整数在比较前需要转换成浮点数。
如果两个比较参数都是整数或者浮点数,直接比较。。。
==只适用于浮点数和整数的比较。最好都用=:=。
下划线变量:
如果一个变量在一个字句中只被使用一次,编译器会提出警告。但以下划线开始,那么编译器不会产生警告信息。
命名不准备使用的变量,增加可读性。方便调试。
Read more...
erlang学习笔记-列表解析和断言
1.列表解析。
1> L=[1,2,3,4] .
[1,2,3,4]
4> lists:map(fun(X) -> 2*X end,L).
[2,4,6,8]
5> [2*X || X <- L].
[2,4,6,8]
[F(X) || X <- L] 代表由F(X)组成的列表,X取值于列表L。||右边用于匹配列表L中元素的模式,左边是一个构造器。
右边模式匹配可以像过滤器一样操作,注意大小写的区别。
6> [X || {a,X} <- [{a,1},{b,2},{c,3},{a,4},hello,"wow"]].
[1,4]
7> [X || {A,X} <- [{a,1},{b,2},{c,3},{a,4},hello,"wow"]].
[1,2,3,4]
2.列表解析快速排序算法。
Read more...
-module(lib_misc). -export([qsort/1]). qsort([]) -> []; qsort([Pivot|T]) -> qsort([X || X <- T, X < Pivot]) ++ [Pivot] ++ qsort([X || X <- T,X >= Pivot]).++中缀添加操作符 19> [1]++[2]++[3,4]. [1,2,3,4] 3.毕达哥拉斯三元组。
pythag(N) ->
[{A,B,C} ||
A <- lists:seq(1,N),
B <- lists:seq(1,N),
C <- lists:seq(1,N),
A+B+C =< N,
A*A+B*B =:= C*C
].
lists:seq(1,N)返回一个1到N组成的列表。
4.断言。
功能:断言是一种用于强化模式匹配功能的结构。
断言序列:
用分号(;)分开的集合,只要有一个True,整个序列就为True。
用逗号(,)分开的集合,必须都为true,整个断言序列才为true。
断言序列的合法语法形式:(表格,p43)
原子true,其他常量(条件,或者绑定变量)求值为false,
断言谓词或BIF(内建函数),比较表达式,算术表达式,布尔表达式,短路布尔表达式
布尔表达式中,orelse,andalso与 or/and 区别:and/or 需要对参数都进行求值。
erlang学习笔记--顺序型编程
妙不可言的函数编程。为什么这么说呢,当我看完第三章时,被erlang的编程方式深深的吸引住了,但是作者总是在我觉得很精妙的地方说:“该方法在实际编程中很少用到”T_T。python也有函数编程的思想,不过一直没有用到过,可能还停留在初级阶段。下面的笔记也只是自己学习中的所悟,可能有着大量的错误,如果你发现我理解的不对,感谢留言指正。请带着怀疑的态度看此笔记。
1、模块。
模块文件存放在扩展名为.erl的文件中,编译完成后的扩展名为.beam。
文件名geometry.erl(博客不支持erlang语法高亮,蛋疼了。。)
-module(geometry).
-export([area/1]).
area({rectangle,Width,Ht}) -> Width * Ht;
area({circle,R}) -> 3.14 * R * R
执行过程:先需要将erlang shell目录移动到代码目录下,查看当前目录命令pwd(),cd(Dir)。
2> c(geometry).
{ok,geometry}
6> geometry:area({rectangle,10,5}).
50
7> geometry:area({circle,1.4}).
6.1544
字句顺序不重要,但调用参数的匹配过程是从上向下的。函数不能处理模式匹配失败的情况,将会抛出一个运行时错误。
2、fun匿名函数
1> Z = fun(X) -> 2*X end.
#Fun<erl_eval.6.82930912>
2> Z(3).
6
这个简单的例子介绍fun函数的用法,用一个"end"做结尾。第三行语句的值为一个函数Z(X)=2*X
以fun为参数的函数
3> Even = fun(X) -> (X rem 2) =:= 0 end.
#Fun<erl_eval.6.82930912>
4> Even(8).
true
5> Even(3).
false
6> lists:map(Even,[1,2,3,4,5,6,7,8]).
[false,true,false,true,false,true,false,true]
7> lists:filter(Even,[1,2,3,4,5,6,7,8]).
[2,4,6,8]
第三个语句,我们定义了一个Even函数,用来求变量是否是偶数,是返回true。
第四第五语句是函数的使用。
第六行将函数Even作为参数,将列表中的每一个元素代入Even,得到的值生成一个新的列表。lists:filter是将满足使Even值为true的列表元素生成一个新列表。
返回fun的函数
11> Fruit = [apple,pear,orange].
[apple,pear,orange]
12> MakeTest = fun(L) -> (fun(X) -> lists:member(X,L)end) end.
#Fun<erl_eval.6.82930912>
13> IsFruit = MakeTest(Fruit).
#Fun<erl_eval.6.82930912>
14> IsFruit(pear).
true
15> IsFruit(dog).
false
17> BoxList = [dog,orange,cat,apple,bear].
[dog,orange,cat,apple,bear]
18> lists:filter(IsFruit,BoxList).
[orange,apple]
11行定义了一个Fruit列表,里面都是水果(⊙﹏⊙b汗)。十二行定义了一个函数MakeTest(L),他的值为一个fun函数,这个fun函数的功能是看变量X是否是L中的元素,是返回True。(感觉就是二元一次方程,你必须知道两个变量才能求得一个结果值)
第13行定义函数IsFruit(X)=lists:member(X,Fruit),当然我这样表示是不正确的,只是为了写得像数学上的函数。正确是IsFruit = fun(X) -> lists:member(X,Fruit) end,这样这个函数的功能变成:看X是否是水果,是返回true。
第14,15行进行了函数测试。十七行定义了一个篮子,里面各种东西,我们要挑出水果,用我们的lists标准库,如果IsFruit为true,那么是水果,则挑拣到另一个篮子里。哇哈哈~
定义自己的抽象流程控制:
这里更是可以举一反三,做你想做的^_^。
书上给了一个for循环控制结构的实现:(语法不支持高亮,就用截图了,不高亮我自己看着别扭)
[caption id="attachment_578" align="alignnone" width="300" caption="erlang编程"]
[/caption]
这是实现了for(i=0,i<10,i++),for i in range(0,10),简单的你可以实现一个for i in range(0,10,2)。
解释一下程序:如果第一个参数值与第二个相同,返回执行 F(Max),否则匹配第二个,F(I)作为列表的头,for(I+1,Max,F)作为列表尾。
如果看到这里,你也会有疑问,为什么不写第二条语句在第一条上面呢?因为交换以后,for(I,Max,F)将满足任何语句,就不会执行第二条语句。编译器也会提示给你:lib_misc.erl:6: Warning: this clause cannot match because a previous clause at line 5 always matches。你的执行将会死循环。当然如果你输入的匹配I>Max,也会进入死循环。
我感觉这将比其他语言的for循环更加灵活。
25> c(lib_misc).
{ok,lib_misc}
26> lib_misc:for(1,10,fun(I) -> I end).
[1,2,3,4,5,6,7,8,9,10]
27> lib_misc:for(1,10,fun(I) -> I*I end).
[1,4,9,16,25,36,49,64,81,100]
28>
编译,26行打印1-10整数列表,27行打印平方列表。
先整理这么多,第二章的笔记是边学边记,第三章是一口气给看完了。⊙﹏⊙b汗
Read more...
[/caption]
这是实现了for(i=0,i<10,i++),for i in range(0,10),简单的你可以实现一个for i in range(0,10,2)。
解释一下程序:如果第一个参数值与第二个相同,返回执行 F(Max),否则匹配第二个,F(I)作为列表的头,for(I+1,Max,F)作为列表尾。
如果看到这里,你也会有疑问,为什么不写第二条语句在第一条上面呢?因为交换以后,for(I,Max,F)将满足任何语句,就不会执行第二条语句。编译器也会提示给你:lib_misc.erl:6: Warning: this clause cannot match because a previous clause at line 5 always matches。你的执行将会死循环。当然如果你输入的匹配I>Max,也会进入死循环。
我感觉这将比其他语言的for循环更加灵活。
25> c(lib_misc).
{ok,lib_misc}
26> lib_misc:for(1,10,fun(I) -> I end).
[1,2,3,4,5,6,7,8,9,10]
27> lib_misc:for(1,10,fun(I) -> I*I end).
[1,4,9,16,25,36,49,64,81,100]
28>
编译,26行打印1-10整数列表,27行打印平方列表。
先整理这么多,第二章的笔记是边学边记,第三章是一口气给看完了。⊙﹏⊙b汗
erlang基本语法学习笔记
在shell下学习erlang的语法
1.输入十六进制:
1> 16#f.
15
输入命令需要在末尾加上一个点号,否则会认为没有输入完整。(第一次安装完成,就迫不及待的在命令行下试了,没有成功,慌了。仔细阅读文档才发现输入不完整。)
2.erlang变量名大写:
13> i=9.
** exception error: no match of right hand side value 9
14> I=9.
9
3.erlang变量的单一赋值:
当执行I=9时,值9就被绑定到I上。没绑定之前是一个自由变量,绑定后变量的值将不会再发生改变。
“=”模式匹配操作符。
17> I=5.
** exception error: no match of right hand side value 5
“Erlang 是一个函数式语言,不存在可变状态。 当多核编程来临的时候,采用不可
变状态所带来的好处是难以估量的。 如果你用 C、Java 这样的传统编程语言为多核 CPU 编写程序,就不得不应付共享内存带来的问题。要想不破坏共享内存,就必须在访问时对其加锁。程序还要保证在操纵共享内存时不会崩溃。 而Erlang没有可变状态,也就没有共享内存,更没有锁,这一切都有利于并行化程序的编写。”
“定义一个变量的词法单元就是这个变量的作用域。因此,如果在一个函数语句范围
内使用 X,那么 X 的值就不能―跳出‖语句之外。在同一个函数的不同子句中,彼此之间也不存在全
局或者共享的私有变量。如果 X 出现在许多个不同的函数当中,那么这些 X 的值也都是各自独立
的。”这个在看完函数后再进行验证。
4.浮点数运算:
18> 5/3.
1.6666666666666667
19> 4/2.
2.0
20> 5 div 3.
1
21> 10 rem 3.
1
22> 4 div 2.
2
23> 4 div 2.0.
** exception error: bad argument in an arithmetic expression
in operator div/2
called as 4 div 2.0
24> 4.0 div 2
24> .
** exception error: bad argument in an arithmetic expression
in operator div/2
called as 4.0 div 2
25> 5/3.0.
1.6666666666666667
经过测试,div运算两边必须是整数。rem取余。
5.erlang原子:
原子是一串以小写字母开头,后跟数字字母或下划线(_)或邮件符号(@)的字符,使用单引号引起来的也是原子。
原子的值就是他自身。
做了几个测试:
37> aaa.
aaa
38> 'aaa'.
aaa
39> "aaa".
"aaa"
40> 111.
111
41> '1111'.
'1111'
42> 'a111'.
a111
43> ''.
''
44> '.
44> '
44> .
'.\n'
45> a'111'.
* 1: syntax error before: '111'
45> +.
* 2: syntax error before: '.'
45> '+'.
'+'
46> AAA.
* 1: variable 'AAA' is unbound
47> 'AAA' .
'AAA'
'单引号是个特殊字符,用来区分原子,"双引号是定义字符串,在后面讲。符合定义的,单引号加与没加一样,不符合的(如:大写字母开头或者数字,或者特殊字符),需要加上单引号作为区分。
6.元组:
将若干个以逗号分割的值用一对花括号括起来,就形成了一个元组。值可以是数值和原子。
从元组获取值:
48> D = {a,5,b} .
{a,5,b}
49> {a,C,B} = D.
{a,5,b}
50> C.
5
51> B.
b
书上的一个例子:
55> Person={person,{name,{first,joe},{last,armstrong}},{footsize,42}}
55> .
{person,{name,{first,joe},{last,armstrong}},{footsize,42}}
56> {_,{_,{_,Who},_},_}=Person.
{person,{name,{first,joe},{last,armstrong}},{footsize,42}}
57> Who.
joe
58>
注意 在前面的样例中,将_作为占位符,表示那些我们不关心的变量。符号_称为匿名变量,与常规变量不同,在同一个模式中的不同地方,各个_所绑定的值不必相同。
7.erlang列表:
用列表存储可变的东西,将若干个以逗号分割的值用一对方括号括起来,就形成了一个列表。列表的第一个元素称为列表的头(head)。除去头,剩下的东西就称为列表的尾(tail)。
例如,如果有列表[1,2,3,4,5],那么列表的头就是整数 1,它的尾为[2,3,4,5]。注意,列表的头可以是任何东西,但是列表的尾通常还是一个列表。
访问列表的头是一个非常高效的操作,因此,实际上所有的列表处理函数都是从提取列表头开始的,先对头进行处理,然后继续处理列表的尾。
erlang列表定义:如果T 是一个列表,那么[H|T]也是一个列表 ,这个列表以H 为头,以T为尾。竖线符号(|)可以将列表的头和尾分隔开来,而[]则是空列表。
58> H = [1,a,{a,b,c}].
[1,a,{a,b,c}]
59> T = [1,2,3].
[1,2,3]
60> [H|T].
[[1,a,{a,b,c}],1,2,3]
提取列表中的值:
62> [Aa|Bb]=H.
[1,a,{a,b,c}]
63> Aa.
1
64> Bb.
[a,{a,b,c}]
8.erlang字符串:
严格来讲,erlang没有字符串,字符串就是一个整数列表,列表中的每一个值都是字符所对应的整数值。
shell打印一串列表值时,只有列表中的所有整数都是可打印字符,它才把这个列表当作字符串来打印:
66> [3,4,5].
[3,4,5]
67> [83,84,85].
"STU"
68> [3,83,84].
[3,83,84]
69> [$a,$b,$c].
"abc"
我们无须死记硬背哪一个整数表示哪一个特定的字符(ASCII码表),可以使用$符号来表示字符的整数值。例如,$a实际上是一个整数,表示字符 a。
命令f()会让shell释放它所绑定过的所有变量。执行这个命令后,所有的变量都变成自由变量。
72> X=333.
333
73> X=111.
** exception error: no match of right hand side value 111
74> f().
ok
75> X=111.
111
终于将第二章看完了,有种眼前一亮的感觉。
Read more...
Erlang研究研究
Erlang程序设计。pdf
这几天突然又迷茫了,再看c和c++的一些注意、要点。看了本《python网络编程》,与自己想学的东西差太多,看到后面就开始蹦跶着看了。
在网上看了一篇文章,决定小小的研究一下erlang,说不定以后用得着。
找了几篇文章
http://zhys9.com/blog/?tag=erlang
http://jbpm.group.iteye.com/group/topic/7938
几本erlang相关的pdf书,从sina的共享文档找的,论坛不上,qq群加了。
开始搞erlang
Read more...