数学与软件

01中的数学
学了数学文化与思维的课程让我开始对数学有了新的认识,我开始不单单以工具的角度看待数学,也开始从思维的角度理解数学。而反思我自己的专业也是一样,软件在外行眼中也许就是一个使用的工具,他们不会去考虑为什么会有这个软件,这个软件是怎么想到的,是怎么实现的。对于我们软件的开发者软件不只是一个工具更是一种思维的创新与体现,作为开发者,相对于工具的使用更需要关注的是一个软件背后的想法与思考。
数学与计算机
计算机之所以叫做计算机,它本来的用途便是计算。二三十年以前,计算机科学基本上还是数学的一个分支。而现在,计算机科学拥有广泛的研究领域和众多的研究人员,在很多方面反过来推动数学发展,从某种意义上可以说是孩子长得比妈妈还高了。
但不管怎么样,这个孩子身上始终流着母亲的血液。这血液是the mathematical underpinning of computer science(计算机科学的数学基础),-- 也就是理论计算机科学。
现代计算机科学和数学的另一个交叉是计算数学/数值分析/科学计算,传统上不包含在理论计算机科学以内。所以本文对计算数学全部予以忽略。
最常和理论计算机科学放在一起的一个词是什么?答:离散数学。这两者的关系是如此密切,以至于它们在不少场合下成为同义词。
传统上,数学是以分析为中心的。数学系的同学要学习三四个学期的数学分析,然后是复变,实变,泛函等等。实变和泛函被很多人认为是现代数学的入门。在物理,化学,工程上应用的,也以分析为主。
随着计算机科学的出现,一些以前不太受到重视的数学分支突然重要起来。人们发现,这些分支处理的数学对象与传统的分析有明显的区别:分析研究的对象是连续的,因而微分,积分成为基本的运算;而这些分支研究的对象是离散的,因而很少有机会进行此类的计算。人们从而称这些分支为“离散数学”。“离散数学”的名字越来越响亮,最后导致以分析为中心的传统数学分支被相对称为“连续数学”。
离散数学经过几十年发展,基本上稳定下来。一般认为,离散数学包含以下学科:
1) 集合论,数理逻辑与元数学。这是整个数学的基础,也是计算机科学的基础。
2) 图论,算法图论;组合数学,组合算法。计算机科学,尤其是理论计算机科学的核心是
算法,而大量的算法建立在图和组合的基础上。
3) 抽象代数。代数是无所不在的,本来在数学中就非常重要。在计算机科学中,人们惊讶地发现代数竟然有如此之多的应用。
但是,理论计算机科学仅仅就是在数学的上面加上“离散”的帽子这么简单吗?一直到大约十几年前,终于有一位大师告诉我们:不是。D.E.Knuth(他有多伟大,我想不用我废话了)在Stanford开设了一门全新的课程Concrete Mathematics。 Concrete这个词在这里有两层含义:
第一,针对abstract而言。Knuth认为,传统数学研究的对象过于抽象,导致对具体的问题
关心不够。他抱怨说,在研究中他需要的数学往往并不存在,所以他只能自己去创造一些数学。为了直接面向应用的需要,他要提倡“具体”的数学。在这里我做一点简单的解释。例如在集合论中,数学家关心的都是最根本的问题–公理系统的各种性质之类。而一些具体集合的性质,各种常见集合,关系,映射都是什么样的,数学家觉得并不重要。然而,在计算机科学中应用的,恰恰就是这些具体的东西。Knuth能够首先看到这一点,不愧为当世计算机第一人。
第二,Concrete是Continuous(连续)加上discrete(离散)。不管连续数学还是离散数学,都是有用的数学!
前面主要是从数学角度来看的。从计算机角度来看,理论计算机科学目前主要的研究领域包括:可计算性理论,算法设计与复杂性分析,密码学与信息安全,分布式计算理论,并行计算理论,网络理论,生物信息计算,计算几何学,程序语言理论等等。这些领域互相交叉,而且新的课题在不断提出,所以很难理出一个头绪来。
下面随便举一些例子。
由于应用需求的推动,密码学现在成为研究的热点。密码学建立在数论(尤其是计算数论),代数,信息论,概率论和随机过程的基础上,有时也用到图论和组合学等。很多人以为密码学就是加密解密,而加密就是用一个函数把数据打乱。这就大错特错了。
现代密码学至少包含以下层次的内容:
第一,密码学的基础。例如,分解一个大数真的很困难吗?能否有一般的工具证明协议正确?
第二,密码学的基本课题。例如,比以前更好的单向函数,签名协议等。
第三,密码学的高级问题。例如,零知识证明的长度,秘密分享的方法。
第四,密码学的新应用。例如,数字现金,叛徒追踪等。
所以计算机与数学是不可分割的,数学让计算机得以诞生,而计算机也推动着数学的发展,让人们发现了它更多的用途。
软件的构思与统计的思维
软件与计算机科学最大的不同便是它的面向对象性,软件是为使用者开发,一个成功的软件并不取决于它编写与开发的复杂,而是在于使用者有良好的使用体验。所以软件的开发并不能只关注自己的想法,而要去关注社会的指向,与其他开发者的成果。这一切都与统计的思维相契合。
通过统计的思维我们能更好的了解用户,了解现状。所谓的大数据分析,无非是用计算机完成了人工无法完成的统计和分析,但是思维和方法并没有变。在统计学的帮助下,我们能知道用户的需求,用户的习惯和用户的爱好,这样我们便可以针对用户和当前的市场决定我们开发的方向。如果不进行统计,只是一味地考虑我们自己的感受,便远离了软件面向对象这一特性。当我们费尽心思将软件实现,但发现无人使用的时候,那无疑是一种时间的浪费。
当今软件数量众多,之所以有些能够有大量的使用者,有的可能无人知晓,在开发之前方向和内容的选择至关重要,而这一切都是来源于用户的喜好,只有通过统计与分析才能将用户的想法知晓。好的开头是成功的一半,对于软件最初的构思至关重要,通过数学的运用便能将这个开头做好。
在统计的过程中,用户的爱好和需求至关重要,而这也是所有商家和软件最关系的东西。我们不认识这些人也没有办法去询问和调查,只有运用数据的分析用统计的原理去得到我们想要的,这也是为什么现在信息值钱的原因。一个人的信息也许他自己会觉得没用,但是在借助数学和计算机的分析之后就能得到很多的东西,甚至可以一定程度上做到预知未来,也就是推算这个人将来的行为,甚至一群人的行为习惯。当我们知道了他们的习惯之后,我们就能分析得到他们的需求再根据现在已有的软件市场情况,去考虑我们开发的方向。
数学在软件编写中的运用
数学对于软件的编写也是极其重要的,很多的算法实现需要很高的数学基础,在算法结构构造的过程中,数学的思维也是必不可少的。
软件编写中一个重要的能力便是将需要需要完成的任务抽象化,在计算机内一切都必须用01的序列表示,一切都是抽象的声明定义,而没有实际的不变实体。而在抽象的过程中数学是最主要的手段,本来实实在在的东西,用数学和数据进行抽象化表示,我们便能在软件中对其进行处理。
空间是现实中一个很具体的东西,它难以在计算机内表示,这时我们借助数学的思维,用坐标表示每一个重要点,这样一个复杂的空间就被变成了便于存储和处理的数据集合。而如果没有这样的数学思想,没有想到将空间数据化,这样的空间我们便无法进行处理。在编写程序的过程中有很多这样的情况,一个实际的东西需要我们处理但是在计算机01的世界里这些没有办法得到表示也就没有办法处理,这时数学的思维就可以帮助我们将这些实际的东西用数字来表达。计算机的运行就是不断的计算,而计算的前提就是所有参与运算的都是已知的数据。所以计算机运行的本质其实就是数学的计算,所以数学的思想能够在计算的过程中起到决定性的作用。
人无法解决的问题电脑也不可能解决,软件能做的只是高速的计算着编写者规定的内容,而这些内容一定是编写者自己理解和掌握的,只不过电脑有更快的运算速度,但是本质的运算并没有变化。
数学对软件的优化
编程是与数学不可分割的过程,一个软件在二进制的运行中其实无非就是在不断的做着数学的运算。而好的运算方式和思想能够帮助一个软件更高效的运行。排序与搜索是所有软件最基本也是最重要的能力,但是不同的排序和搜索的方式需要的运算次数是不同的,好的方法能够大大提高软件运行的效率,这种提高是指数型的,而这一切都要靠软件开发者对于运算的理解和数学能力来决定的。
例如n个元素的排序操作,普通的冒泡排序和
选择排序需要n的平方次的运算,而更高级的希尔排序的运算期望次数却只有n的1.3次方。这已经是很大的提高,但是如果开发者的数学能力和对于二分这种数学思想的理解足够到位,那么更优化的归并排序和堆排序只需要仅仅nlogn的运算次数,这和最初的n的平方相差巨大。这已经是作用强大的数学思想对排序进行了极大的优化,但是这却依旧不是极限,如果开发者对于数学的理解达到了极高的境界,那么计数排序和桶排序仅仅需要n+k次运算。
数学对排序的优化将n方次的运算优化到了极限的n+k次运算,试想同样的一百万数据的排序需求,一个不懂数学的开发者所开发出来的软件需要一万亿次运算,普通的电脑需要运行一万秒也就是接近三个小时,但是一个懂数学的开发者运用数学的思维与工具对排序进行优化,他做出来的软件仅仅需要0.02秒便可以完成这一操作。这还仅仅是排序这一个环节,在所有的环节数学都可以对软件进行优化,同样的功能在数学的优化下原来需要运行几个小时甚至几天的过程只需要不到一秒就可以完成。在这种情况下原来的软件还有谁会去使用。
优化是数学对于软件进行的量的变化,虽然能够完成的功能不变,但是运行的时间和空间的需求会大大减少,这样能够让用户得到更好的使用体验。
数学对开发者的影响
在大学中我们会学习很多数学,虽然以后可能会忘记某些数学知识,但是思维能力的水平却实实在在的提高了。这为我们学习其他知识提供了良好,我们能够更快更深刻的理解一个抽象的事物。正如之前所说软件的世界是一个抽象的世界,抽象的人,抽象的物。数学好的人,抽象能力强,比较善于从复杂的现象中
概括出与核心问题相关的简化了的数学模型。有了数学模型,才容易探讨什么是这个问题的一般性解决方案,以及某个解决方案能够成立的边界条件。并且把解决方案数学化表达,进而比较不同解决方案的优劣,比如收敛速度或者系统误差等等。数学的重要性在于:重要的不是获得的知识,而是发展思维能力。
通过一个学期的学习,我越来越意识到数学对于我所学习的专业是多么的重要,这种重要不仅仅体现在对思维能力的要求,更体现在如果你不知道相关的数学知识,呢么你就无法解决这个问题。通常在说,真正的解决一个问题,你必须找到问题的所在;找到问题所在之后,你必须能用某种方式去描述它,这就要用到数学,编写软件解决任何一个问题,都要首先把它抽象成数学模型,然后再对其数学分析思考出相应的解决办法,也就是所谓的算法,最后才是用编程语言将算法实现。
有人可能会说,需要用到算法、需要进行优化时再去研究就好。但没有学过的永远不是你的,你很容易就能在网上找到很好的算法和代码,但是没有学过你根本就没法去想到这一切,连搜什么大概都不会知道。假如我们一时兴起,要去爬缙云山,没问题,那种程度的山,只要有脚就能爬。但是如果换成现在流行的登山步道,可能有些身体不好的人就得放弃了。如果我心大要去爬泰山呢?开山到山下,穿个好点的鞋子、好点的衣服、提前休息保留体力,可能也不是太大的问题。可如果我想要站在世界的最高点,要去挑战珠穆朗玛峰,那全世界没几个人办得到,而且没人能说自己不用训练心情好了准备一下就能做到。为什么Google公司会这么重视算法和效率?因为你做的程序不是给几十个、几百个人用而已,而是同一时间有几百万,甚至上千万人使用。一个人慢0.1s,一百万人就是十万秒,就直接超过一天了。
如果只是想当一个普通的程序工程师,数学不好也许还行。但是如果作为一个高层的架构,没有很好的数学思维能力是不行的。只有在你手里有锤子的时候,你看什么才都会是个钉子。想想你如果没有学过算法和数据结构,没有这些能力,可能你的大部分程序需要自己写排序的话,都还会是傻傻的冒泡吧,反正对于大部分程序来说,现在的电脑都已经够快了,这点时间差对于你,也就是在执行测试时多泡杯茶(看会儿手机)而已吧。但是你将永远不会去感受到那种新鲜,好玩,挑战的乐趣。
虽然是这么说,但是大部分软件的同学都是学完考完之后就把数学抛在脑后,大多数编码工作中也完全用不上学的那些东西。所以,“数学很重要”,这句话,似乎对于大家来说,始终只是飘在天上的一句话,随风飘逝罢了。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值