SlideShare a Scribd company logo
Clojure的魅力伯岩boyan@taobao.com2010-08-10
AgendaClojure基础Clojure语法和数据结构Sequences与java交互并发实现缺陷总结2
What is clojure?A dynamic programming language for JVMClojure is a LispClojure is functionalSupporting ConcurrencyDesigned for the JVMHistory3 years in development,released 10/2007Authror: Rich HickeyHomepage:  http://clojure.org3
Clojure is a LispClojure是Lisp的一种方言,就像scheme、common lisp也是Lisp的方言一样。Clojure同样也是Homoiconicity(同像性)Homoiconicity:编程语言的一种属性,是指该语言的基本表现形式本身同时也是该语言自身的数据结构。Homoiconicity使得元编程更容易Code vs. Data小核心Sequences抽象宏(macro)非OO模型4
Hello WorldREPL——交互式编程环境user=> (println "hello world")        hello world        nil5
Code vs. Data从代码角度                              (println "hello world")函数           参数   从数据角度                              (println "hello world")一个list6
Clojure的数据类型Integer   –123456789Double 1.234BigDecimal 1.234mRatios(分数)22/7Strings  “hello”Characters  \a \b \cSymbols   foo barKeywords  :foo :barBooleans  true falseNull      nilRegex patterns   #“[a-z]*\d+”2010-08-10淘宝内部分享-伯岩7
数据结构List单向链表(1 2 3 4 5) (list \a \b\ c)\Vector类似数组,索引访问[1 2 3 4 5] [foo bar]Map   key/value{:a 1 :b 2} {1 “hello” 2 “world”}Set集合,不能重复#{foo bar}全部可嵌套2010-08-10淘宝内部分享-伯岩8
语法前缀运算符(+ 1 2 3)  (println (str “hello “ “world”))(op …), op可以为少数几个special formMacro返回函数的表达式数据结构即代码语法 == 数据结构的解释9
传统的求值模型2010—8-10淘宝内部分享-伯岩10
Clojure的求值模型2010-08-10淘宝内部分享-伯岩11
Symbols可以理解成变量,绑定特定的值user=> a   java.lang.Exception: Unable to resolve symbol: a in this context (NO_SOURCE_FILE:0)user=> (def a 1)   #'user/a   user=> a   1user=> (let [a 1] a)   1user=> (binding [a 2] a)    22010-08-10淘宝内部分享-伯岩12
let和bindinglet是用词法作用域的不可变值“遮蔽”了外部的symbol绑定值。Binding则是创建thread-local级别的symbol绑定值。例子:(def foo 1)(defn print-foo [] (println foo))(let [foo 2] (print-foo))     =>1(binding [foo 2] (print-foo)) =>22010-08-10淘宝内部分享-伯岩13
Special forms(def name init-value?)  定义全局变量(if test then-expr else-expr)条件语句(quote form)返回不会被执行的form(fn name? ([params* ] exprs*)+)定义函数其他:let loop recur do new  .  throw try set! var14
Macro——宏Macro是Clojure元编程的主要方式什么是Macro?模板语言C语言的预处理器unless:(defmacro unless [test expr]      `(if ~test nil ~expr)) (if ${test} nil ${expr})15
Macro`Syntax quote       标记为模板~Unquote            替代value~@Splicing unquote   拼接list的内容foo#  Auto-gensym        创建唯一符号名称16
函数Clojure是FP——函数式编程语言函数是First-Class Values作为参数作为返回值保存为变量(def square (fn [x] (* x x)))    (squre 3)  => 9    (defn square [x] (* x x))17
高阶函数18
高阶函数以信息流的方式去组织代码,高阶函数带来了约定接口的抽象19range:integersmap:fibfilter:even?
语法小结20
Sequences传统Lisp中list的抽象(cons item seq)将item插入seq的首部创建新的seq(seq coll)如果集合为空,返回nil,否则返回集合的seq(first seq)  == (car list)返回seq的第一个元素(rest seq)   == (cdr list)返回seq除第一个元素之外的元组,如果没有则为nil21
Sequence(1)22
Sequence(2)(iterate inc 0)自然数集合(use ‘[clojure.contrib.lazy-seqs :only(primes)])   (def ordinals-and-primes (map vector (iterate inc 1)  primes))[1 2] [2 3] [3 5]…[n nth-primes]的vector集合延迟和无穷doall dorun 强制seq的副作用触发23
Sequence(3)(first (System/getProperties))#<Entry java.runtime.name=OpenJDK Runtime Environment>(rest (.getBytes “hello”))(101 108 108 111)(sort (re-seq #“\w+” “the quick brown fox”))(“brown” “fox” “quick” “the”)(count (file-seq (File. ".")))(with-open [rdr (reader “hello.clj”)]             (count (line-seq rdr)))TODO(xml-seq)24
Java InteropsClojue Strings  == Java StringsClojure Numbers == Java NumbersClojure Collections实现java Collection接口Clojure函数实现Runnable和Callable接口Clojure可以继承和实现Java的类和接口Clojure的seq库可以直接使用在Java的String和Array以及Iterable25
Java Interops实例(. Math PI)   Math/PI(new java.util.Date) (java.util.Date.)(. date getYear)(.getYear date)(.. System getProperties (get “java.version”))(doto (JFrame.) (add (Jlabel. “hello world”)) pack show)(int-array 3)(aset a 0 1) (aget a 0) (alength a)26
Persistent Data StructuresClojure的数据结构都是immutable的每次更新都将创建一个新的数据结构复制的开销解决方案:结构共享,Persistent数据结构Git的tree结构Couch DB的索引Clojure的数据结构27
Persistent Data Structures28
Persistent Data Structures29
Clojure的并发并发的一个关键点在于如何管理可变状态(mutable states)锁的方式:直接引用可变状态采用锁来保护消息传递的方式:将可变状态作为不可变的消息传递没有共享状态Clojure的方式:间接引用不可变的持久数据结构STM更新状态没有锁30
典型的OO方式一致性需要用户来保证31
Clojure——间接引用值不可变取值需要经过deref32
四种模型Ref、Atomic、Agent和ThreadLocal vars协作/独立:状态是否与其他状态共同作用同步/异步:状态的更新是同步还是异步33
Ref和事务(def songs (ref #{}))创建ref@songs取ref的值(dosync (refset songs #{“dangerous”}))改变ref指向的值,需要包装在事务里(def singers (ref #{}))   (dosync (ref-set sings #{“dangerous”})        (ref-set singers #{“MJ”}))协作更新多个ref(dosync (alter songs conj “heal the world”))查询并更新(dosync (commute songs conj “heal the world”))更新操作是可交换的,符合交换律34
STM使用(dosync …)包装软事务内存,内存型数据库:ACI,没有D基于MVCC实现——多版本并发控制所有对ref的读都将在事务开始的时候“看到”一个一致的快照(Snapshot),以及该事务内对ref所做的更改。所有在事务内对ref所做的更改,在外部看来都将是一个时间点触发的。读不会阻碍读/写,写不会阻碍读没有死锁,活锁的隐患35
Atomic管理独立的可变状态,类似Java的AtomicReference(内部实现)(def mem (atom {}))创建atom@meme取值(reset! mem {:a 1})设值,无需事务(swap! mem assoc :b 2)查询并更新(compare-and-set! mem oldValue newValue)原子的比较更新适合实现缓存 memoize36
Agent用于异步的状态更新(def counter (agent 0))创建agent@counter取值(send counter inc)发送任务,适合非阻塞任务(send-off counter inc)发送任务,适合阻塞型任务,如IO操作(await counter)等待任务结束每个agent每次只执行一个任务,同一个线程发送的任务有序可以在事务中使用,那么当且仅当事务commit成功的时候发送任务  实现bin log37
Clojure的实现——函数动态编译成bytecode使用asm 3.0暂时没有AOT编译模式每个函数都是一个新的class实现clojure.lang.IFn接口根据函数的参数个数实现对应的系列invoke方法参数和返回值都以Object类型存在可变参数基于sequences实现Clojure Hacking Guide38
Clojure的实现——调用函数调用就是Java的方法调用没有额外的类型系统和转换没有额外的参数对Java的调用:直接调用 or 反射没有包装、捕获异常和动态转换Type hints和类型推断允许直接调用(def class-name [^Class c]                 (.getName c))*warn-on-reflection* 提示反射,避免反射39
Clojure的实现——STMMVCC——Multiversion Concurrency Control每个ref维持一张版本列表事务开始和提交的时候都分配一个时间戳提交成功的时候,将commit时间戳和新的值加入Ref的版本列表Write Conflictabort and retryBargeCommute,不做写冲突检查,不取得ref的ownership,计算立即可见,但是在commit的时候如果发现ref值被其他事务更改了,重新运行计算。Software Transactional Memory40
Clojure的实现——Atomic和AgentAtomic,内部封装AtomicReferenceAgent全局线程池send使用固定大小线程池 cpus+2适合计算密集型任务send-off使用Cached ThreadPool适合IO型任务(shutdown-agents)关闭线程池41
没有谈到的……函数的递归调用let/fn/loop的destructuring列表推断(Lisp comprehesions)关系集合代数Multimethods并行计算(pmap pvalues pcalls)……2004-5-31淘宝内部分享-烟客42
一些缺憾没有尾递归优化recur仅能在方法内,goto指令受限于JVM的安全模型所有JVM之上的函数式语言都有这个问题使用Java数值类型的包装类型以及Cojure独有的RatioInteger,Long,BigInteger etc.数值在heap上,算术运算性能欠佳Agent无法自定义线程池线程没有命名,非daemon无法高效利用线程池弱类型,没有scala那样强大的类型推断能力,需要用户接入:type hint括号复括号,FP,小众中的小众43
参考资料http://clojure.org/http://clojuredocs.org/不错的网络教程clojure相关资料我的Blog书籍推荐:44
Thanks!2010-08-10淘宝内部分享-伯岩45

More Related Content

PPTX
Clojure概览
PDF
Clojure简介与应用
PDF
Google protocol buffers简析
PPTX
Linux c++ 编程之链接与装载 -提高篇--v0.3--20120509
PPTX
Linux c++ 编程之链接与装载 -基础篇--v0.3--20120509
PDF
Jni攻略之八――操作对象的构造方法
DOC
深入剖析Concurrent hashmap中的同步机制(上)
PDF
getPDF.aspx
Clojure概览
Clojure简介与应用
Google protocol buffers简析
Linux c++ 编程之链接与装载 -提高篇--v0.3--20120509
Linux c++ 编程之链接与装载 -基础篇--v0.3--20120509
Jni攻略之八――操作对象的构造方法
深入剖析Concurrent hashmap中的同步机制(上)
getPDF.aspx

What's hot (19)

PPTX
Golangintro
PDF
少年科技人雜誌 2015 年八月
PPT
Java7 fork join framework and closures
PPT
Exodus重构和向apollo迁移
PDF
Programming python - part 1
PPT
Jvm内存管理基础
PDF
Row Set初步学习V1.1
DOC
Java华为面试题
PPT
线程与并发
DOC
J2ee面试知识
PDF
Hash map导致cpu100% 的分析
PDF
Node.js开发体验
ODP
Object-Based Programming Part II
PDF
lambda/closure – JavaScript、Python、Scala 到 Java SE 7
DOC
Java程序员面试之葵花宝典
PPTX
Ecma script edition5-小试
PDF
[圣思园][Java SE]Io 3
PPTX
Baidu LSP and DISQL for Log Analysis
Golangintro
少年科技人雜誌 2015 年八月
Java7 fork join framework and closures
Exodus重构和向apollo迁移
Programming python - part 1
Jvm内存管理基础
Row Set初步学习V1.1
Java华为面试题
线程与并发
J2ee面试知识
Hash map导致cpu100% 的分析
Node.js开发体验
Object-Based Programming Part II
lambda/closure – JavaScript、Python、Scala 到 Java SE 7
Java程序员面试之葵花宝典
Ecma script edition5-小试
[圣思园][Java SE]Io 3
Baidu LSP and DISQL for Log Analysis
Ad

Viewers also liked (20)

PDF
A Dive Into Clojure
PDF
Patterns
PDF
Writing Macros
PPT
A little exercise with clojure macro
PDF
不自然なcar/ナチュラルにconsして
PDF
Clojure Macros Workshop: LambdaJam 2013 / CUFP 2013
ODP
Clojure: Practical functional approach on JVM
PDF
入門ClojureScript
PDF
Macros in Clojure
PDF
Continuation Passing Style and Macros in Clojure - Jan 2012
PPTX
我在 Mac 上的常用开发工具
PDF
Clojure 1.8 Direct-Linking WWH
PDF
Stefan Richter - Writing simple, readable and robust code: Examples in Java, ...
PDF
Clojureシンタックスハイライター開発から考えるこれからのlispに必要なもの
PDF
Elixir introd
KEY
(map Clojure everyday-tasks)
KEY
PDF
Introduction to clojure
PDF
DSL in Clojure
PDF
プログラミング言語Clojureのニャンパスでの活用事例
A Dive Into Clojure
Patterns
Writing Macros
A little exercise with clojure macro
不自然なcar/ナチュラルにconsして
Clojure Macros Workshop: LambdaJam 2013 / CUFP 2013
Clojure: Practical functional approach on JVM
入門ClojureScript
Macros in Clojure
Continuation Passing Style and Macros in Clojure - Jan 2012
我在 Mac 上的常用开发工具
Clojure 1.8 Direct-Linking WWH
Stefan Richter - Writing simple, readable and robust code: Examples in Java, ...
Clojureシンタックスハイライター開発から考えるこれからのlispに必要なもの
Elixir introd
(map Clojure everyday-tasks)
Introduction to clojure
DSL in Clojure
プログラミング言語Clojureのニャンパスでの活用事例
Ad

Similar to Clojure的魅力 (20)

PPT
Java Script 引擎技术
PDF
000 北京圣思园教育科技有限公司第一期面授培训大纲
PPT
千呼萬喚始出來的Java SE 7
PPT
beidakejian
PDF
潜力无限的编程语言Javascript
PPT
Java并发编程培训
PPT
Java并发编程培训
PPTX
IOS入门分享
PDF
Clojure
PDF
J2ee经典学习笔记
PDF
Web前端标准在各浏览器中的实现差异
PPT
IKVM.NET 深入敵營的 Java
PPT
Struts Mitac(1)
PPT
Hibernate教程
ODP
Java DSL与动态代码生成技术的应用 (上集:DSL部分)
PDF
Javascript 闭包
PDF
D2-ETao-show
PDF
Javascript primer plus
PPT
Java 1(Java概述)
DOC
中远公司 Java培训资料
Java Script 引擎技术
000 北京圣思园教育科技有限公司第一期面授培训大纲
千呼萬喚始出來的Java SE 7
beidakejian
潜力无限的编程语言Javascript
Java并发编程培训
Java并发编程培训
IOS入门分享
Clojure
J2ee经典学习笔记
Web前端标准在各浏览器中的实现差异
IKVM.NET 深入敵營的 Java
Struts Mitac(1)
Hibernate教程
Java DSL与动态代码生成技术的应用 (上集:DSL部分)
Javascript 闭包
D2-ETao-show
Javascript primer plus
Java 1(Java概述)
中远公司 Java培训资料

More from dennis zhuang (15)

PDF
一个 Mongodb command 的前世今生
PDF
Erlang scheduler
PDF
Java 与 CPU 高速缓存
PDF
Mesos intro
PPTX
QCon - 一次 Clojure Web 编程实战
PPTX
CQL 实现
PDF
Hystrix 介绍
PDF
AVOSCloud简介——万象移动云平台
PDF
Avoscloud 2
PPTX
点评新架构
ODP
Ihome inaction 篇外篇之fp介绍
PPTX
Nio trick and trap
PPTX
Aviator——轻量级表达式执行引擎
PDF
Erlang简介
PPTX
Java多线程常见陷阱
一个 Mongodb command 的前世今生
Erlang scheduler
Java 与 CPU 高速缓存
Mesos intro
QCon - 一次 Clojure Web 编程实战
CQL 实现
Hystrix 介绍
AVOSCloud简介——万象移动云平台
Avoscloud 2
点评新架构
Ihome inaction 篇外篇之fp介绍
Nio trick and trap
Aviator——轻量级表达式执行引擎
Erlang简介
Java多线程常见陷阱

Recently uploaded (20)

PPTX
3分钟读懂福特汉姆大学毕业证Fordham毕业证学历认证
PPTX
3分钟读懂南威尔士大学毕业证UCB毕业证学历认证
PPTX
3分钟读懂拉夫堡大学毕业证LU毕业证学历认证
PPTX
3分钟读懂索尔福德大学毕业证Salford毕业证学历认证
PDF
01_Course_Introduction(20210916課後更新).pdf
PPTX
3分钟读懂渥太华大学毕业证UO毕业证学历认证
PPTX
模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板
PPTX
3分钟读懂肯塔基大学毕业证UK毕业证学历认证
PPTX
3分钟读懂诺里奇艺术大学毕业证NUA毕业证学历认证
PPTX
A Digital Transformation Methodology.pptx
PPTX
3分钟读懂佩珀代因大学毕业证Pepperdine毕业证学历认证
PPTX
3分钟读懂圣安德鲁斯大学毕业证StAnd毕业证学历认证
PPTX
3分钟读懂皇家艺术学院毕业证RCA毕业证学历认证
PDF
黑客出手,分数我有!安全可靠的技术支持,让你的GPA瞬间提升,留学之路更加顺畅!【微信:viphuzhao】
PPTX
3分钟读懂纽曼大学毕业证Newman毕业证学历认证
PDF
黑客技术,安全提分不是梦!我们采用最新的数据破解和隐藏技术,精准定位并修改你的成绩,同时采用深度隐藏技术确保你的操作不被发现。价格实惠,流程快速,事后无痕...
PPTX
3分钟读懂贵湖大学毕业证U of G毕业证学历认证
PPTX
3分钟读懂滑铁卢大学毕业证Waterloo毕业证学历认证
PPTX
3分钟读懂圭尔夫大学毕业证U of G毕业证学历认证
PPTX
3分钟读懂伦敦政治经济学院毕业证LSE毕业证学历认证
3分钟读懂福特汉姆大学毕业证Fordham毕业证学历认证
3分钟读懂南威尔士大学毕业证UCB毕业证学历认证
3分钟读懂拉夫堡大学毕业证LU毕业证学历认证
3分钟读懂索尔福德大学毕业证Salford毕业证学历认证
01_Course_Introduction(20210916課後更新).pdf
3分钟读懂渥太华大学毕业证UO毕业证学历认证
模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板模板
3分钟读懂肯塔基大学毕业证UK毕业证学历认证
3分钟读懂诺里奇艺术大学毕业证NUA毕业证学历认证
A Digital Transformation Methodology.pptx
3分钟读懂佩珀代因大学毕业证Pepperdine毕业证学历认证
3分钟读懂圣安德鲁斯大学毕业证StAnd毕业证学历认证
3分钟读懂皇家艺术学院毕业证RCA毕业证学历认证
黑客出手,分数我有!安全可靠的技术支持,让你的GPA瞬间提升,留学之路更加顺畅!【微信:viphuzhao】
3分钟读懂纽曼大学毕业证Newman毕业证学历认证
黑客技术,安全提分不是梦!我们采用最新的数据破解和隐藏技术,精准定位并修改你的成绩,同时采用深度隐藏技术确保你的操作不被发现。价格实惠,流程快速,事后无痕...
3分钟读懂贵湖大学毕业证U of G毕业证学历认证
3分钟读懂滑铁卢大学毕业证Waterloo毕业证学历认证
3分钟读懂圭尔夫大学毕业证U of G毕业证学历认证
3分钟读懂伦敦政治经济学院毕业证LSE毕业证学历认证

Clojure的魅力