斯坦福编程范式
A. C语言之父——丹尼斯·里奇
人们对里奇的纪念,远不及对乔布斯铺天盖地的悼念。可是,里奇值得人们那样去做。
还是有人出来说了句公道话。
“史蒂夫·乔布斯去世引发了巨大的反响,这当然合情合理。即便影响实际上更为广泛,丹尼斯却不为公众所知”,罗伯·派克说。罗伯是一名在Google工作的程序员,作为业界的传奇性人物,曾经与里奇在着名的贝尔实验室共事20年。
周三晚间,派克在Google+上发表消息称,在与病魔进行长久的抗争后,里奇于上周末在新泽西的家中溘然长逝。虽然在技术圈内引起大量反响,但在主流媒体上,里奇却没有得到同巨大影响相称的悼念。丹尼斯·里奇作为C语言之父,和贝尔实验室资深研究员肯·汤姆森一起使用C语言开发了Unix,当今世界大量依赖的操作系统,其中包括史蒂夫·乔布斯治下的苹果帝国。
“现下互联网基本都在用这两样东西:C语言和UNIX”,派克对《连线》杂志称,“浏览器是用C语言写的。UNIX的内核——基本上是因特网运作的基础——也是用C写的。Web服务器也是用C语言写的,如果不是的话,那就是用Java或者C++写的,两者都是C语言的派生;要不就是python或者Ruby,用C语言实现的。然后我几乎敢保证,运行这些程序的网络硬件,是用C语言开发的软件驱动的。”
“几乎很难夸大丹尼斯在信息经济基础设施方面无所不在的影响力。”
他补充说,Windows曾经也是用C语言编写,而UNIX同时也支撑了苹果桌面操作系统Mac OS X,以及iPhone与iPad的操作系统iOS。“如果说乔布斯是台前之王,那里奇就是幕后之王。”MIT电气工程与计算机系教授Martin Rinard如此评价道。Rinard也是计算机科学与人工智能实验室的成员。
“乔布斯的过人之处在于其品位独特,打造人们为之着迷并引人注目的产品。而里奇却擅长于开发一些技术人员使用的基础设施,天天被人们使用却不为人知。”
从B语言到C语言
为了更好开发UNIX,丹尼斯·里奇而发明了C语言。最初的UNIX内核使用汇编语言编写,之后他们很快决定要用一种高级语言,让他们更好的驾驭操作系统中的复杂数据。1970年左右,他们尝试使用Fortran,不过没有达到预期目标。接着,在汤姆森创立的B语言基础上,里奇提出了一门新语言
不管你是从哪里听来的消息,B语言得名于汤姆森的妻子Bonnie,抑或是BCPL,一门剑桥于60年代中期开发的语言。
B语言是一种解释性语言——意味着它由一个运行于CPU之上的中间件解释执行——而C却是一门编译语言。它被翻译成机器代码,在CPU上直接执行。即便如此,C当时被认为是一门高级语言。C语言提供了里奇和汤姆森想要的灵活性,却也很快。
关于里奇一直流传的一个笑话是:C语言同时拥有了“汇编语言的强大能力以及...汇编语言的便利性”。换句话说,他承认C语言并不完美,并且十分接近硬件层次。如今C语言被认为是一门低级语言而不是高级语言。不过这个笑话并不公平。C语言提供了真正的数据结构概念,从这个角度来说已经足够高级了。
“当你在编写一个大型程序——比如UNIX——你必须管理好各种各样模块之间的交互:所有用户、文件系统、磁盘、程序执行等等。而有效的管理则需要良好的数据表示,这就是所谓的数据结构”,派克说。
“在没有数据结构组织的情况下,编写一个与UNIX一样一致和优雅的内核基本上是不可能的。需要一个机制组织好数据,而Fortran却不擅长于此。”
在那个时候,写一个操作系统并不多见,这也给了里奇和汤姆森机会,在70年代末把操作系统移植到其它平台。“从此UNIX洪水之门被打开”,派克说,“这全都多亏有了C语言。”
苹果、微软及其他
与此同时,C语言也开始传播到全世界,从贝尔实验室到全世界的大学,也到了微软,一个在80年代异军突起的软件公司。“C语言的开发是一个重大的飞跃,是个很好的折衷...C语言达到了完美的平衡,让你在较高层次高效率开发的同时,却不失去对每处细节的控制”,NVIDIA和贝尔的首席科学家兼斯坦福大学工程系教授Bill Dally说。“它为之后数十年来软件开发定下了基调。”
正如派克指出的那样,C语言内置的数据结构后来发展出面向对象范式,被现代编程语言如C++和Java大量采用。
1973年,里奇发表了关于这门语言的论文,被认为是革命开始的标志。5年后,他和同事布莱恩·克尼汉(Brian Kernighan)发布了C语言的权威着作:《C程序设计语言》。该书最早是克尼汉为C语言编写的教程,后来他拉着丹尼斯一起把书写完。
当派克还在多伦多大学读本科的时候,在一个因病返家的下午里读到了这本书。“那本参考手册相对于其他的手册而言,简直就是清晰和可读的典范。毋庸置疑是一部经典之作。”,他说,“我生病躺床上翻一翻,没想到竟让我忘记了病痛。”
和许多大学生一样,Pike那时已经开始使用C语言了。由于贝尔实验室开始分发UNIX源代码,它逐渐风靡大学校园。此外,UNIX还催生了现代开源运动。这并不是什么言过其实,里奇的影响之大怎么说都不为过。即便里奇在1983年获得的图灵奖和1998年获得的国家技术勋章也不能完全彰显他的贡献。
在克尼汉和派克眼中,里奇是一个少有的孤僻的人。“我和他一同工作了超过20个年头,但还是觉得不是很了解他这个人”,派克说。但这并不是他低调的理由。史蒂夫·乔布斯也是一个孤僻的人,只不过保持低调只使得人们对他的崇拜有增无减。
里奇所处的时代和工作环境与乔布斯千差万别,这也许是他未得到应得纪念的原因。但是,他留下的遗产总有大佬能够明白。“众所周知牛顿说过他是站在巨人的肩膀上”,克尼汉说,“我们都站在丹尼斯的肩膀上。”
B. 如何系统地自学 Python
是否非常想学好 Python,一方面被琐事纠缠,一直没能动手,另一方面,担心学习成本太高,心里默默敲着退堂鼓?
幸运的是,Python 是一门初学者友好的编程语言,想要完全掌握它,你不必花上太多的时间和精力。
Python 的设计哲学之一就是简单易学,体现在两个方面:
语法简洁明了:相对 Ruby 和 Perl,它的语法特性不多不少,大多数都很简单直接,不玩儿玄学。
切入点很多:Python 可以让你可以做很多事情,科学计算和数据分析、爬虫、Web 网站、游戏、命令行实用工具等等等等,总有一个是你感兴趣并且愿意投入时间的。
- 用一种方法,最好是只有一种方法来做一件事。
废话不多说,学会一门语言的捷径只有一个: Getting Started
¶ 起步阶段
任何一种编程语言都包含两个部分:硬知识和软知识,起步阶段的主要任务是掌握硬知识。
硬知识
“硬知识”指的是编程语言的语法、算法和数据结构、编程范式等,例如:变量和类型、循环语句、分支、函数、类。这部分知识也是具有普适性的,看上去是掌握了一种语法,实际是建立了一种思维。例如:让一个 Java 程序员去学习 Python,他可以很快的将 Java 中的学到的面向对象的知识 map 到 Python 中来,因此能够快速掌握 Python 中面向对象的特性。
如果你是刚开始学习编程的新手,一本可靠的语法书是非常重要的。它看上去可能非常枯燥乏味,但对于建立稳固的编程思维是必不可少。
下面列出了一些适合初学者入门的教学材料:
廖雪峰的 Python 教程 Python 中文教程的翘楚,专为刚刚步入程序世界的小白打造。
笨方法学 Python 这本书在讲解 Python 的语法成分时,还附带大量可实践的例子,非常适合快速起步。
The Hitchhiker’s Guide to Python! 这本指南着重于 Python 的最佳实践,不管你是 Python 专家还是新手,都能获得极大的帮助。
Python 的哲学:
学习也是一样,虽然推荐了多种学习资料,但实际学习的时候,最好只选择其中的一个,坚持看完。
必要的时候,可能需要阅读讲解数据结构和算法的书,这些知识对于理解和使用 Python 中的对象模型有着很大的帮助。
软知识
“软知识”则是特定语言环境下的语法技巧、类库的使用、IDE的选择等等。这一部分,即使完全不了解不会使用,也不会妨碍你去编程,只不过写出的程序,看上去显得“傻”了些。
对这些知识的学习,取决于你尝试解决的问题的领域和深度。对初学者而言,起步阶段极易走火,或者在选择 Python 版本时徘徊不决,一会儿看 2.7 一会儿又转到 3.0,或者徜徉在类库的大海中无法自拔,Scrapy,Numpy,Django 什么都要试试,或者参与编辑器圣战、大括号缩进探究、操作系统辩论赛等无意义活动,或者整天跪舔语法糖,老想着怎么一行代码把所有的事情做完,或者去构想圣洁的性能安全通用性健壮性全部满分的解决方案。
很多“大牛”都会告诫初学者,用这个用那个,少走弯路,这样反而把初学者推向了真正的弯路。
还不如告诉初学者,学习本来就是个需要你去走弯路出 Bug,只能脚踏实地,没有奇迹只有狗屎的过程。
选择一个方向先走下去,哪怕脏丑差,走不动了再看看有没有更好的解决途径。
自己走了弯路,你才知道这么做的好处,才能理解为什么人们可以手写状态机去匹配却偏要发明正则表达式,为什么面向过程可以解决却偏要面向对象,为什么我可以操纵每一根指针却偏要自动管理内存,为什么我可以嵌套回调却偏要用 Promise...
更重要的是,你会明白,高层次的解决方法都是对低层次的封装,并不是任何情况下都是最有效最合适的。
技术涌进就像波浪一样,那些陈旧的封存已久的技术,消退了迟早还会涌回的。就像现在移动端应用、手游和 HTML5 的火热,某些方面不正在重演过去 PC 的那些历史么?
因此,不要担心自己走错路误了终身,坚持并保持进步才是正道。
起步阶段的核心任务是掌握硬知识,软知识做适当了解,有了稳固的根,粗壮的枝干,才能长出浓密的叶子,结出甜美的果实。
¶ 发展阶段
完成了基础知识的学习,必定会感到一阵空虚,怀疑这些语法知识是不是真的有用。
没错,你的怀疑是非常正确的。要让 Python 发挥出它的价值,当然不能停留在语法层面。
发展阶段的核心任务,就是“跳出 Python,拥抱世界”。
在你面前会有多个分支:科学计算和数据分析、爬虫、Web 网站、游戏、命令行实用工具等等等等,这些都不是仅仅知道 Python 语法就能解决的问题。
拿爬虫举例,如果你对计算机网络,HTTP 协议,HTML,文本编码,JSON 一无所知,你能做好这部分的工作么?而你在起步阶段的基础知识也同样重要,如果你连循环递归怎么写都还要查文档,连 BFS 都不知道怎么实现,这就像工匠做石凳每次起锤都要思考锤子怎么使用一样,非常低效。
在这个阶段,不可避免要接触大量类库,阅读大量书籍的。
类库方面
“Awesome Python 项目”:vinta/awesome-python · GitHub
这里列出了你在尝试解决各种实际问题时,Python 社区已有的工具型类库,如下图所示:
vinta/awesome-python
你可以按照实际需求,寻找你需要的类库。
至于相关类库如何使用,必须掌握的技能便是阅读文档。由于开源社区大多数文档都是英文写成的,所以,英语不好的同学,需要恶补下。
书籍方面
这里我只列出一些我觉得比较有一些帮助的书籍,详细的请看豆瓣的书评:
科学和数据分析:
❖“集体智慧编程”:集体智慧编程 (豆瓣)
❖“数学之美”:数学之美 (豆瓣)
❖“统计学习方法”:统计学习方法 (豆瓣)
❖“Pattern Recognition And Machine Learning”:Pattern Recognition And Machine Learning (豆瓣)
❖“数据科学实战”:数据科学实战 (豆瓣)
❖“数据检索导论”:信息检索导论 (豆瓣)
爬虫:
❖“HTTP 权威指南”:HTTP权威指南 (豆瓣)
Web 网站:
❖“HTML & CSS 设计与构建网站”:HTML & CSS设计与构建网站 (豆瓣)
...
列到这里已经不需要继续了。
聪明的你一定会发现上面的大部分书籍,并不是讲 Python 的书,而更多的是专业知识。
事实上,这里所谓“跳出 Python,拥抱世界”,其实是发现 Python 和专业知识相结合,能够解决很多实际问题。这个阶段能走到什么程度,更多的取决于自己的专业知识。
¶ 深入阶段
这个阶段的你,对 Python 几乎了如指掌,那么你一定知道 Python 是用 C 语言实现的。
可是 Python 对象的“动态特征”是怎么用相对底层,连自动内存管理都没有的C语言实现的呢?这时候就不能停留在表面了,勇敢的拆开 Python 的黑盒子,深入到语言的内部,去看它的历史,读它的源码,才能真正理解它的设计思路。
这里推荐一本书:
“Python 源码剖析”:Python源码剖析 (豆瓣)
这本书把 Python 源码中最核心的部分,给出了详细的阐释,不过阅读此书需要对 C 语言内存模型和指针有着很好的理解。
另外,Python 本身是一门杂糅多种范式的动态语言,也就是说,相对于 C 的过程式、 Haskell 等的函数式、Java 基于类的面向对象而言,它都不够纯粹。换而言之,编程语言的“道学”,在 Python 中只能有限的体悟。学习某种编程范式时,从那些面向这种范式更加纯粹的语言出发,才能有更深刻的理解,也能了解到 Python 语言的根源。
这里推荐一门公开课
“编程范式”:斯坦福大学公开课:编程范式
讲师高屋建瓴,从各种编程范式的代表语言出发,给出了每种编程范式最核心的思想。
值得一提的是,这门课程对C语言有非常深入的讲解,例如C语言的范型和内存管理。这些知识,对阅读 Python 源码也有大有帮助。
Python 的许多最佳实践都隐藏在那些众所周知的框架和类库中,例如 Django、Tornado 等等。在它们的源代码中淘金,也是个不错的选择。
¶ 最后的话
每个人学编程的道路都是不一样的,其实大都殊途同归,没有迷路的人只有不能坚持的人!
希望想学 Python 想学编程的同学,不要犹豫了,看完这篇文章,
Just Getting Started !!!
C. 如何系统地自学 Python
按照这个大纲按部就班的学习,就能系统的学习Python了!
阶段一:Python开发基础
Python全栈开发与人工智能之Python开发基础知识学习内容包括:Python基础语法、数据类型、字符编码、文件操作、函数、装饰器、迭代器、内置方法、常用模块等。
阶段二:Python高级编程和数据库开发
Python全栈开发与人工智能之Python高级编程和数据库开发知识学习内容包括:面向对象开发、Socket网络编程、线程、进程、队列、IO多路模型、Mysql数据库开发等。
阶段三:前端开发
Python全栈开发与人工智能之前端开发知识学习内容包括:Html、CSS、JavaScript开发、Jquery&bootstrap开发、前端框架VUE开发等。
阶段四:WEB框架开发
Python全栈开发与人工智能之WEB框架开发学习内容包括:Django框架基础、Django框架进阶、BBS+Blog实战项目开发、缓存和队列中间件、Flask框架学习、Tornado框架学习、Restful API等。
阶段五:爬虫开发
Python全栈开发与人工智能之爬虫开发学习内容包括:爬虫开发实战。
阶段六:全栈项目实战
Python全栈开发与人工智能之全栈项目实战学习内容包括:企业应用工具学习、CRM客户关系管理系统开发、路飞学城在线教育平台开发等。
阶段七:算法&设计模式
阶段八:数据分析
Python全栈开发与人工智能之数据分析学习内容包括:金融量化分析。
阶段九:机器学习、图像识别、NLP自然语言处理
Python全栈开发与人工智能之人工智能学习内容包括:机器学习、图形识别、人工智能玩具开发等。
阶段十:Linux系统&百万级并发架构解决方案
阶段十一:高并发语言GO开发
Python全栈开发与人工智能之高并发语言GO开发学习内容包括:GO语言基础、数据类型与文件IO操作、函数和面向对象、并发编程等。
D. 人工智能需要学习哪些课程
人工智能专业学习的主要课程有认知心理学、神经科学基础、人类的记忆与学习、语言与思维、计算神经工程等。人工智能专业是中国高校人才计划设立的专业,旨在培养中国人工智能产业的应用型人才,推动人工智能一级学科建设。
E. 网易公开课的大学课程
网易公开课课程内容不断更新,以下为部分课程举例。 《编程方法学》全28集 翻译至第28集
《7个颠覆你思想的演讲》 全7集 翻译至第7集(网易首翻1-5集)
《经济学》 全10集 翻译至第10集(网易首翻1-5集)
《商业领袖和企业家》 全4集 翻译至第4集(网易首翻1-4集)
《人与计算机的互动》全10集 翻译至第10集
《扎克伯格谈facebook创业过程》 全9集 翻译至第9集
《iphone开发教程2010年冬》 全28集 翻译至第26集
《机器学习课程》 全20集 翻译至第20集
《抽象编程》 全27集 翻译至第27集
《编程范式》 全27集 翻译至第27集
《法律学》 全6集 翻译至第2集
《机器人学》全16集 翻译至第2集
《健康图书馆》全80集 翻译至第80集
《临床解剖学》 全14集 翻译至第14集
《癌症综合研究》全56集 翻译至第56集
《从生物学看人类行为》 全25集 翻译至第25集
《非裔美国人历史——当代自由斗争》全18集 翻译至第10集
《斯坦福创意与艺术协会讲座》 全16集 翻译至第0集
《忘掉你学过的MBA——戴维谈创业37 signals》全11集 翻译至11集
《全球气候与能源计划》 全12集 翻译至第1集 《国际座谈会》 全17集 翻译至第17集(网易首翻1-12集)
《领导能力简介》 全5集 翻译至第5集(网易首翻1-5集)
《能源和环境》 全11集 翻译至第1集
《人性》 全12集 翻译至第12集
《科技世界的领导能力》 全15集 翻译至第15集 《电影哲学》 全4集 翻译至第4集(网易首翻1-4集)
《西方世界的爱情哲学》 全4集 翻译至第4集(网易首翻1-2集)
《音乐的各种声音》 全1集 翻译至第1集
《振动与波》 全23集 翻译至第23集
《单变量微积分》 全35集 翻译至第15集
《微分方程》 全33集 翻译至第15集
《媒体、教育、市场》 全14集 翻译至第14集
《商业及领导能力》 全16集 翻译至第1集
《热力学与动力学》 全36集 翻译至第30集
《搜索黑洞》 全6集 翻译至第6集
《城市面貌——过去和未来》全4集 翻译至第0集
《经典力学》 全35集 翻译至第35集
《生物学导论》 全35集 翻译至第35集
《微积分重点》 全18集 翻译至第18集
《多变量微积分》全35集 翻译至第35集
《化学原理》 全36集 翻译至第31集
《算法导论》 全6集 翻译至第6集
《计算机科学及编程导论》 全24集 翻译至第23集 《幸福课》 全23集 翻译至第23集(网易首翻1-5集)
《公正—该如何做是好?》 全12集 翻译至第12集
《计算机科学导论》 全22集 翻译至第0集
《2006年计算机课程》 全32集(缺第3、5、7、集) 翻译至第0集
《2005年计算机课程》 全15集 翻译至第0集
《计算机科学cs50》 全20集 翻译至第17集
《科学与烹饪》 翻译至22集 《空气污染》集数:5 类型:科学 环境 社会
《十分钟英语史》集数:10 类型:历史 文学
《银行业危机-源起与后果》集数:7 类型:金融 经济 《古希腊历史简介》 全24集 翻译至第8集 (1-8集字幕由人人字幕组提供)
《聆听音乐》 全23集 翻译至第10集(网易首翻5-10集)(1-4集字幕由人人字幕组提供)
《死亡》 全26集 翻译至第11集(网易首翻8-21集)(1-7集字幕由人人字幕组提供)
《心理学导论》 全20集 翻译至第18集(网易首翻9-18集)(1-8集字幕由人人字幕组提供)
《政治哲学导论》 全24集 翻译至第14集(网易首翻1-14集)
《金融市场》 全26集 翻译至第17集(网易首翻14-17集)(1-13集字幕由人人字幕组提供)
《博弈论》 全24集 翻译至第9集 (1-9集字幕由人人字幕组提供)
《欧洲文明》 全24集 翻译至第23集 (1-23集字幕由TLF字幕组提供)
《1871年后的法国》 全24集 翻译至第3集 (1-3集字幕由人人字幕组提供)
《基础物理》 全24集 翻译至第23集 (1-5集字幕由人人字幕组提供)
《罗马建筑》 全23集 翻译至第4集 (1-4集字幕由TLF字幕组提供)
《天体物理学之探索和争议》 全24集 翻译至第10集 (1-10集字幕由TLF字幕组提供)
《生物医学工程探索》 全25集 翻译至第12集 (1-12集字幕由人人字幕组提供)
《新生有机化学》 全37集 翻译至第10集 (1-10集字幕由人人字幕组提供)
《进化、生态和行为原理》 全36集 翻译至第4集 (1-4集字幕由TLF字幕组提供)
《1945年后的美国小说》 全25集 翻译至第3集 (1-3集字幕由人人字幕组提供)
《美国内战与重建,1845-1877》 全27集 翻译至第5集 (1-5集字幕由人人字幕组提供)
《全球人口增长问题》 全24集 翻译至第7集 (1-7集字幕由TLF字幕组提供)
《有关食物的心理学、生物学和政治学》 全23集 翻译至第7集 (1-7集字幕由人人字幕组提供)
《弥尔顿》 全24集
《文学理论导论》 全26集
《现代诗歌》 全25集
《解读但丁》 全24集
《旧约全书导论 》全24集
《新约及其历史背景》 全26集 《尼采的心灵与自然》 全7集
《哲学概论》 全17集 《综合生物学》 全39集
《社会认知心理学》 全25集
《数据统计分析》 全42集
《世界各地区人民和国家》 全19集(缺第17、18、20)
《大灾难时期的伦理和公共健康》 全14集 点击右上方的“播放”按钮,或者直接点击课时按钮,经过短暂的缓冲之后便可以开始在线收看课程,缓冲时会显示课时和该课时视频大小。由于是在线收看,因此课程的视频和音频不可能达到高清的效果,不过完全可以满足授课的需要,并且在wifi环境下播放流畅,丝毫不会卡顿。此外手机本身需要支持MP4格式才可以收看在线课程,不过这项要求基本Android平台手机都可以达到。网易公开课的课程视频对手机的硬件要求并不高,小编用setcpu将CPU频率由1GHz降至500MHz后,仍然可以流畅播放。
播放过程中可以点击屏幕任意位置叫出播放控制按钮,用户可以暂停/播放视屏,快进和快退,以及拖动进度条来跳转至视频的任意位置。但是小编在实际使用中发现,在某些情况下,拖动进度条会造成程序失去响应,实际能够使用的只有快进/快退和播放/暂停三个按键。小编之后又用另一台手机Nexus S测试,发现强行关闭的问题仍然存在。 1、收集世界多所知名学府授课视频;
2、wifi环境下播放流畅。 1、当视频在线播放时拖动进度条,若遇网络环境不太好,或进程多系统繁忙,偶尔会出现无响应,造成程序强行关闭;
2、课程翻译进度较慢。
F. 讲C语言内存管理的书籍或者博客
我推荐的是斯坦福的一门公开课 -- 《编程范式》。不是题主说的博客或者书,但是个人觉得很好用,希望对你有帮助。
还有一些其他的编程语言,如方案、Python等。
我只看到了多线程同步的一部分,个人的感觉受益于它。如果以后还有别的发现,愿意及时分享给大家。
G. 放弃手工标记数据,斯坦福大学开发弱监督编程范式Snorkel
手工标记大量数据始终是开发机器学习的一大瓶颈。斯坦福AI Lab的研究人员探讨了一种通过编程方式生成训练数据的“弱监督”范式,并介绍了他们的开源Snorkel框架。
近年来,机器学习 (ML) 对现实世界的影响越来越大。这在很大程度上是由于深度学习模型的出现,使得从业者可以在基准数据集上获得 state-of-the-art 的分数,而无需任何手工特征设计。考虑到诸如 TensorFlow 和 PyTorch 等多种开源 ML 框架的可用性,以及大量可用的最先进的模型,可以说,高质量的 ML 模型现在几乎成为一种商品化资源了。然而,有一个隐藏的问题:这些模型依赖于大量手工标记的训练数据。
这些手工标记的训练集创建起来既昂贵又耗时 —— 通常需要几个月甚至几年的时间、花费大量人力来收集、清理和调试 —— 尤其是在需要领域专业知识的情况下。除此之外,任务经常会在现实世界中发生变化和演变。例如,标记指南、粒度或下游用例都经常发生变化,需要重新标记 (例如,不要只将评论分类为正面或负面,还要引入一个中性类别)。
由于这些原因,从业者越来越多地转向一种较弱的监管形式,例如利用外部知识库、模式 / 规则或其他分类器启发式地生成训练数据。从本质上来讲,这些都是以编程方式生成训练数据的方法,或者更简洁地说,编程训练数据 (programming training data)。
在本文中,我们首先回顾了 ML 中由标记训练数据驱动的一些领域,然后描述了我们对建模和整合各种监督源的研究。我们还讨论了为大规模多任务机制构建数据管理系统的设想,这种系统使用数十或数百个弱监督的动态任务,以复杂、多样的方式交互。
回顾:如何获得更多有标签的训练数据?
ML 中的许多传统研究方法也同样受到对标记训练数据的需求的推动。我们首先将这些方法与弱监督方法 (weak supervision) 区分开来:弱监督是利用来自主题领域专家(subject matter experts,简称 SME) 的更高级别和 / 或更嘈杂的输入。
目前主流方法的一个关键问题是,由领域专家直接给大量数据加标签是很昂贵的:例如,为医学成像研究构建大型数据集更加困难,因为跟研究生不同,放射科医生可不会接受一点小恩小惠就愿意为你标记数据。因此,在 ML 中,许多经过深入研究的工作线都是由于获取标记训练数据的瓶颈所致:
在主动学习 (active learning) 中,目标是让领域专家为估计对模型最有价值的数据点贴标签,从而更有效地利用领域专家。在标准的监督学习设置中,这意味着选择要标记的新数据点。例如,我们可以选择靠近当前模型决策边界的乳房 X 线照片,并要求放射科医生仅给这些照片进行标记。但是,我们也可以只要求对这些数据点进行较弱的监督,在这种情况下,主动学习与弱监督是完美互补的;这方面的例子可以参考 (Druck, settle, and McCallum 2009)。
在半监督学习 (semi-supervised learning ) 设置中,我们的目标是用一个小的标记训练集和一个更大的未标记数据集。然后使用关于平滑度、低维结构或距离度量的假设来利用未标记数据 (作为生成模型的一部分,或作为一个判别模型的正则项,或学习一个紧凑的数据表示);参考阅读见 (Chapelle, Scholkopf, and Zien 2009)。从广义上讲,半监督学习的理念不是从 SME 那里寻求更多输入,而是利用领域和任务不可知的假设来利用未经标记的数据,而这些数据通常可以以低成本大量获得。最近的方法使用生成对抗网络 (Salimans et al. 2016)、启发式转换模型 (Laine and Aila 2016) 和其他生成方法来有效地帮助规范化决策边界。
在典型的迁移学习 (transfer learning )设置 中,目标是将一个或多个已经在不同数据集上训练过的模型应用于我们的数据集和任务;相关的综述见 (Pan 和 Yang 2010)。例如,我们可能已经有身体其他部位肿瘤的大型训练集,并在此基础上训练了分类器,然后希望将其应用到我们的乳房 X 光检查任务中。在当今的深度学习社区中,一种常见的迁移学习方法是在一个大数据集上对模型进行 “预训练”,然后在感兴趣的任务上对其进行 “微调”。另一个相关的领域是多任务学习 (multi-task learning),其中几个任务是共同学习的 (Caruna 1993; Augenstein, Vlachos, and Maynard 2015)。
上述范例可能让我们得以不用向领域专家合作者寻求额外的训练标签。然而,对某些数据进行标记是不可避免的。如果我们要求他们提供各种类型的更高级、或不那么精确的监督形式,这些形式可以更快、更简便地获取,会怎么样呢?例如,如果我们的放射科医生可以花一个下午的时间来标记一组启发式的资源或其他资源,如果处理得当,这些资源可以有效地替代成千上万的训练标签,那会怎么样呢 ?
将领域知识注入 AI
从 历史 的角度来看,试图 “编程” 人工智能 (即注入领域知识) 并不是什么新鲜想法,但现在提出这个问题的主要新颖之处在于,AI 从未像现在这样强大,同时在可解释性和可控制性方面,它还是一个 “黑盒”。
在 20 世纪 70 年代和 80 年代,AI 的重点是专家系统,它将来自领域专家的手工策划的事实和规则的知识库结合起来,并使用推理引擎来应用它们。20 世纪 90 年代,ML 开始作为将知识集成到 AI 系统的工具获得成功,并承诺以强大而灵活的方式从标记的训练数据自动实现这一点。
经典的 (非表示学习)ML 方法通常有两个领域专家输入端口。首先,这些模型通常比现代模型的复杂度要低得多,这意味着可以使用更少的手工标记数据。其次,这些模型依赖于手工设计的特性,这些特性为编码、修改和与模型的数据基本表示形式交互提供了一种直接的方法。然而,特性工程不管在过去还是现在通常都被认为是 ML 专家的任务,他们通常会花费整个博士生涯来为特定的任务设计特性。
进入深度学习模型:由于它们具有跨许多领域和任务自动学习表示的强大能力,它们在很大程度上避免了特性工程的任务。然而,它们大部分是完整的黑盒子,除了标记大量的训练集和调整网络架构外,普通开发人员对它们几乎没有控制权。在许多意义上,它们代表了旧的专家系统脆弱但易于控制的规则的对立面 —— 它们灵活但难以控制。
这使我们从一个略微不同的角度回到了最初的问题:我们如何利用我们的领域知识或任务专业知识来编写现代深度学习模型?有没有办法将旧的基于规则的专家系统的直接性与这些现代 ML 方法的灵活性和强大功能结合起来?
代码作为监督:通过编程训练 ML
Snorkel 是我们为支持和 探索 这种与 ML 的新型交互而构建的一个系统。在 Snorkel中,我们不使用手工标记的训练数据,而是要求用户编写标记函数 (labeling functions, LF),即用于标记未标记数据子集的黑盒代码片段。
然后,我们可以使用一组这样的 LF 来为 ML 模型标记训练数据。因为标记函数只是任意的代码片段,所以它们可以对任意信号进行编码:模式、启发式、外部数据资源、来自群众工作者的嘈杂标签、弱分类器等等。而且,作为代码,我们可以获得所有其他相关的好处,比如模块化、可重用性和可调试性。例如,如果我们的建模目标发生了变化,我们可以调整标记函数来快速适应!
一个问题是,标记函数会产生有噪声的输出,这些输出可能会重叠和冲突,从而产生不太理想的训练标签。在 Snorkel 中,我们使用数据编程方法对这些标签进行去噪,该方法包括三个步骤:
1. 我们将标记函数应用于未标记的数据。
2. 我们使用一个生成模型来在没有任何标记数据的条件下学习标记函数的准确性,并相应地对它们的输出进行加权。我们甚至可以自动学习它们的关联结构。
3. 生成模型输出一组概率训练标签,我们可以使用这些标签来训练一个强大、灵活的判别模型 (如深度神经网络),它将泛化到标记函数表示的信号之外。
可以认为,这整个 pipeline 为 “编程”ML 模型提供了一种简单、稳健且与模型无关的方法!
标记函数 (Labeling Functions)
从生物医学文献中提取结构化信息是最能激励我们的应用之一:大量有用的信息被有效地锁在数百万篇科学论文的密集非结构化文本中。我们希望用机器学习来提取这些信息,进而使用这些信息来诊断遗传性疾病。
考虑这样一个任务:从科学文献中提取某种化学 - 疾病的关系。我们可能没有足够大的标记训练数据集来完成这项任务。然而,在生物医学领域,存在着丰富的知识本体、词典等资源,其中包括各种化学与疾病名称数据、各种类型的已知化学 - 疾病关系数据库等,我们可以利用这些资源来为我们的任务提供弱监督。此外,我们还可以与生物学领域的合作者一起提出一系列特定于任务的启发式、正则表达式模式、经验法则和负标签生成策略。
作为一种表示载体的生成模型
在我们的方法中,我们认为标记函数隐含地描述了一个生成模型。让我们来快速复习一下:给定数据点 x,以及我们想要预测的未知标签 y,在判别方法中,我们直接对P(y|x) 建模,而在生成方法中,我们对 P(x,y) = P(x|y)P(y) 建模。在我们的例子中,我们建模一个训练集标记的过程 P(L,y),其中 L 是由对象 x 的标记函数生成的标签,y 是对应的 (未知的) 真实标签。通过学习生成模型,并直接估计 P(L|y),我们本质上是在根据它们如何重叠和冲突来学习标记函数的相对准确性 (注意,我们不需要知道 y!)
我们使用这个估计的生成模型在标签函数上训练一个噪声感知版本的最终判别模型。为了做到这一点,生成模型推断出训练数据的未知标签的概率,然后我们最小化关于这些概率的判别模型的预期损失。
估计这些生成模型的参数可能非常棘手,特别是当使用的标记函数之间存在统计依赖性时。在 Data Programming: Creating Large Training Sets, Quickly(https://arxiv.org/abs/1605.07723) 这篇论文中,我们证明了给定足够的标记函数的条件下,可以得到与监督方法相同的 asymptotic scaling。我们还研究了如何在不使用标记数据的情况下学习标记函数之间的相关性,以及如何显着提高性能。
Snorkel:一个开源的框架
在我们最近发表的关于 Snorkel 的论文 (https://arxiv.org/abs/1711.10160) 中,我们发现在各种实际应用中,这种与现代 ML 模型交互的新方法非常有效!包括:
1. 在一个关于 Snorkel 的研讨会上,我们进行了一项用户研究,比较了教 SMEs 使用Snorkel 的效率,以及花同样的时间进行纯手工标记数据的效率。我们发现,使用Snorkel 构建模型不仅快了 2.8 倍,而且平均预测性能也提高了 45.5%。
2. 在与斯坦福大学、美国退伍军人事务部和美国食品和药物管理局的研究人员合作的两个真实的文本关系提取任务,以及其他四个基准文本和图像任务中,我们发现,与baseline 技术相比,Snorkel 平均提高了 132%。
3. 我们 探索 了如何对用户提供的标记函数建模的新的权衡空间,从而得到了一个基于规则的优化器,用于加速迭代开发周期。
下一步:大规模多任务弱监管
我们实验室正在进行各种努力,将 Snorkel 设想的弱监督交互模型扩展到其他模式,如格式丰富的数据和图像、使用自然语言的监督任务和自动生成标签函数!
在技术方面,我们感兴趣的是扩展 Snorkel 的核心数据编程模型,使其更容易指定具有更高级别接口(如自然语言) 的标记函数,以及结合其他类型的弱监督 (如数据增强)。
多任务学习 (MTL) 场景的普及也引发了这样一个问题:当嘈杂的、可能相关的标签源现在要标记多个相关任务时会发生什么?我们是否可以通过对这些任务进行联合建模来获益?我们在一个新的多任务感知版本的 Snorkel,即 Snorkel MeTaL 中解决了这些问题,它可以支持多任务弱监管源,为一个或多个相关任务提供噪声标签。
我们考虑的一个例子是设置具有不同粒度的标签源。例如,假设我们打算训练一个细粒度的命名实体识别 (NER) 模型来标记特定类型的人和位置,并且我们有一些细粒度的嘈杂标签,例如标记 “律师” 与 “医生”,或 “银行” 与 “医院”;以及有些是粗粒度的,例如标记 “人” 与 “地点”。通过将这些资源表示为标记不同层次相关的任务,我们可以联合建模它们的准确性,并重新加权和组合它们的多任务标签,从而创建更清晰、智能聚合的多任务训练数据,从而提高最终 MTL 模型的性能。
我们相信,为 MTL 构建数据管理系统最激动人心的方面将围绕大规模多任务机制(massively multi-task regime),在这种机制中,数十到数百个弱监督 (因而高度动态)的任务以复杂、多样的方式交互。
虽然迄今为止大多数 MTL 工作都考虑最多处理由静态手工标记训练集定义的少数几项任务,但世界正在迅速发展成组织 (无论是大公司、学术实验室还是在线社区) 都要维护数以百计的弱监督、快速变化且相互依赖的建模任务。此外,由于这些任务是弱监督的,开发人员可以在数小时或数天内 (而不是数月或数年) 添加、删除或更改任务 (即训练集),这可能需要重新训练整个模型。
在最近的一篇论文 The Role of Massively Multi-Task and Weak Supervision in Software 2.0 (http://cidrdb.org/cidr2019/papers/p58-ratner-cidr19.pdf) 中,我们概述了针对上述问题的一些初步想法,设想了一个大规模的多任务设置,其中 MTL 模型有效地用作一个训练由不同开发人员弱标记的数据的中央存储库,然后组合在一个中央“mother” 多任务模型中。
不管确切的形式因素是什么,很明显,MTL 技术在未来有许多令人兴奋的进展 —— 不仅是新的模型架构,而且还与迁移学习方法、新的弱监督方法、新的软件开发和系统范例日益统一。
原文:
https://ai.stanford.e/blog/weak-supervision/
Snorkel:
http://snorkel.stanford.e/
欢迎同时关注微信公众号: IT 科技 森
每天分享IT小技巧、 科技 数码新闻!