敏捷开发概述

敏捷开发

敏捷开发(Agile development)php

目录

[隐藏]

[编辑]前端

 

敏捷开发概述

  敏捷开发是一种以人为核心、迭代、按部就班的开发方法。在敏捷开发中,软件项目的构建被切分红多个子项目,各个子项目的成果都通过测试,具有集成和可运行的特征。换言之,就是把一个大项目分为多个相互联系,但也可独立运行的小项目,并分别完成,在此过程当中软件一直处于可以使用状态。编程

[编辑]架构

 

敏捷开发的路线[1]

  Image:敏捷开发的路线图.jpg

  图:敏捷开发的路线图框架

  Test-Driven Development,测试驱动开发工具

  它是敏捷开发的最重要的部分。在ThoughtWorks,咱们实现任何一个功能都是从测试开始,首先对业务需求进行分析,分解为一个一个的Story,记录在Story Card上。而后两我的同时坐在电脑前面,一我的依照Story,从业务需求的角度来编写测试代码,另外一我的看着他而且进行思考,若是有不一样的意见就会提出来进行讨论,直到达成共识,这样写出来的测试代码就真实反映了业务功能需求。接着由另外一我的控制键盘,编写该测试代码的实现。若是没有测试代码,就不能编写功能的实现代码。先写测试代码,可以让开发人员明确目标,就是让测试经过。单元测试

  Continuous Integration,持续集成。学习

  在以往的软件开发过程当中,集成是一件很痛苦的事情,一般很长时间才会作一次集成,这样的话,会引起不少问题,好比 build未经过或者单元测试失败。敏捷开发中提倡持续集成,一天以内集成十几回甚至几十次,如此频繁的集成能尽可能减小冲突,因为集成很频繁,每一次集成的改变也不多,即便集成失败也容易定位错误。一次集成要作哪些事情呢?它至少包括:得到全部源代码、编译源代码、运行全部测试,包括单元测试、功能测试等;确认编译和测试是否经过,最后发送报告。固然也会作一些其它的任务,好比说代码分析、测试覆盖率分析等等。在咱们公司里,开发人员的桌上有一个火山灯用来标志集成的状态,若是是黄灯,表示正在集成;若是是绿灯,表示上一次集成经过,开发人员在这时候得到的代码是可用而可靠的;若是显示为红灯,就要当心了,上一次集成未经过,须要尽快定位失败缘由从而让灯变绿。在持续集成上,咱们公司使用的是本身开发的产品CruiseControl。测试

  Refactoring,重构。优化

  相信你们对它都很熟悉了,有不少不少的书用来介绍重构,最著名的是Martin的《重构》,Joshua的《从重构到模式》等。重构是在不改变系统外部行为下,对内部结构进行整理优化,使得代码尽可能简单、优美、可扩展。在以往开发中,一般是在有需求过来,如今的系统架构不容易实现,从而对原有系统进行重构;或者在开发过程当中有剩余时间了,对如今代码进行重构整理。可是在敏捷开发中,重构贯穿于整个开发流程,每一次开发者check in代码以前,都要对所写代码进行重构,让代码达到clean code that works。值得注意的是,在重构时,每一次改变要尽量小,用单元测试来保证重构是否引发冲突,而且不仅是对实现代码进行重构,若是测试代码中有重复,也要对它进行重构。

  Pair-Programming,结对编程。

  在敏捷开发中,作任何事情都是Pair的,包括分析、写测试、写实现代码或者重构。Pair作事有不少好处,两我的在一块儿探讨很容易产生思想的火花,也不容易走上偏路。在咱们公司,还有不少事都是Pair来作,好比Pair学习,Pair翻译,Pair作PPT,关于这个话题,钱钱同窗有一篇颇有名的文章对它进行介绍,名为Pair Programming (结对编程)。

  Stand up,站立会议。

  天天早上,项目组的全部成员都会站立进行一次会议,因为是站立的,因此时间不会很长,通常来讲是15-20分钟。会议的内容并非需求分析、任务分配等,而是每一个人都回答三个问题:1. 你昨天作了什么?2. 你今天要作什么? 3. 你遇到了哪些困难?站立会议让团队进行交流,彼此相互熟悉工做内容,若是有人曾经遇到过和你相似的问题,那么在站立会议后,他就会和你进行讨论。

  Frequent Releases,小版本发布。

  在敏捷开发中,不会出现这种状况,拿到需求之后就闭门造车,直到最后才将产品交付给客户,而是尽可能多的产品发布,通常以周、月为单位。这样,客户每隔一段时间就会拿到发布的产品进行试用,而咱们能够从客户那获得更多的反馈来改进产品。正由于发布频繁,每个版本新增的功能简单,不须要复杂的设计,这样文档和设计就在很大程度上简化了。又由于简单设计,没有复杂的架构,因此客户有新的需求或者需求进行变更,也能很快的适应。

  Minimal Documentation,较少的文档。

  其实敏捷开发中并非没有文档,而是有大量的文档,即测试。这些测试代码真实的反应了客户的需求以及系统API 的用法,若是有新人加入团队,最快的熟悉项目的方法就是给他看测试代码,而比一边看着文档一边进行debug要高效。若是用书面文档或者注释,某天代码变化了,须要对这些文档进行更新。一旦忘记更新文档,就会出现代码和文档不匹配的状况,这更加会让人迷惑。而在敏捷中并不会出现,由于只有测试变化了,代码才会变化,测试是真实反应代码的。这时有人会问:代码不写注释行吗?通常来讲好的代码不是须要大量的注释吗?其实简单可读的代码才是好的代码,既然简单可读了,别人一看就可以看懂,这时候根本不须要对代码进行任何注释。若你以为这段代码不加注释的话别人可能看不懂,就表示设计还不够简单,须要对它进行重构。

  Collaborative Focus,以合做为中心,表现为代码共享。

  在敏捷开发中,代码是归团队全部而不是哪些模块的代码属于哪些人,每一个人都有权利得到系统任何一部分的代码而后修改它,若是有人看到某些代码不爽的话,那他可以对这部分代码重构而不须要征求代码做者的赞成,极可能也不知道是谁写的这部分代码。这样每一个人都能熟悉系统的代码,即便团队的人员变更,也没有风险。

  Customer Engagement ,现场客户。

  敏捷开发中,客户是与开发团队一块儿工做的,团队到客户现场进行开发或者邀请客户到团队公司里来开发。若是开发过程当中有什么问题或者产品通过一个迭代后,可以以最快速度获得客户的反馈。

  Automated Testing ,自动化测试。

  为了减少人力或者重复劳动,全部的测试包括单元测试、功能测试或集成测试等都是自动化的,这对QA人员提出了更高的要求。他们要熟悉开发语言、自动化测试工具,可以编写自动化测试脚本或者用工具录制。咱们公司在自动化测试上作了大量的工做,包括Selenium开源项目。

  Adaptive Planning,可调整计划。

  敏捷开发中计划是可调整的,并非像以往的开发过程当中,需求分析->概要设计->详细设计->开发 ->测试->交付,每个阶段都是有计划的进行,一个阶段结束便开始下一个阶段。而敏捷开发中只有一次一次的迭代,小版本的发布,根据客户反馈随时做出相应的调整和变化。

  敏捷开发过程与传统的开发过程有很大不一样,在这过程当中,团队是有激情有活力的,可以适应更大的变化,作出更高质量的软件。

[编辑]

 

敏捷开发的特色

  敏捷方法主要有两个特色,这也是其区别于其余方法,尤为是重型方法的最主要特征:

  (1)敏捷开发方法是“适应性”(Adaptive)而非“预设性” (Predictive)。

  这里说的预设性,能够经过通常性工程项目的作法理解,好比土木工程,在这类工程实践中,有比较稳定的需求,同时建设项目的要求也相对固定,因此此类项目一般很是强调施工前的设计规划。只要图纸设计得合理并考虑充分,施工队伍能够彻底遵守图纸顺利建造,而且能够很方便地把图纸划分为许多更小的部分交给不一样的施工人员分别完成。

  然而,在软件开发的项目中,这些稳定的因素却很难寻求。软件的设计难处在于软件需求的不稳定,从而致使软件过程的不可预测。可是传统的控制项目模式都是试图对一个软件开发项目在很长的时间跨度内作出详细的计划,而后依计划进行开发。因此,这类方法在不可预测的环境下,很难适应变化,甚至是拒绝变化。

  与之相反的敏捷方法则是欢迎变化,目的就是成为适应变化的过程,甚至能容许改变自身来适应变化。因此称之为适应性方法。

  (2)敏捷开发方法是“面向人” (people oriented)而非“面向过程”(process oriented)。

  Matin Flower认为:“在敏捷开发过程当中,人是第一位的,过程是第二位的。因此就我的来讲,应该能够从各类不一样的过程当中找到真正适合本身的过程。”这与软件工程理论提倡的先过程后人正好相反。 (续致信网上一页内容)

  在传统的软件开发工做中,项目团队分配工做的重点是明确角色的定义,以我的的能力去适应角色,而角色的定义就是为了保证过程的实施,即我的以资源的方式被分配给角色,同时,资源是能够替代的,而角色不能够替代。

  然而,传统软件开发的这些方法在敏捷开发方式中被彻底颠覆。敏捷开发试图使软件开发工做可以利用人的特色,充分发挥人的创造能力。

  敏捷开发的目的是创建起一个项目团队全员参与到软件开发中,包括设定软件开发流程的管理人员,只有这样软件开发流程才有可接受性。同时敏捷开发要求研发人员独立自主在技术上进行决策,由于他们是最了解什么技术是须要和不须要的。再者,敏捷开发特别重视项目团队中的信息交流,有调查显示:“项目失败的缘由最终均可追溯到信息没有及时准确地传递到应该接受它的人。”

[编辑]

 

敏捷开发的价值观

  实际上敏捷开发运动在数年前就开始了,但它正式开始的标志是2001年2月的“敏捷宣言”(Agile Manifesto),这项宣言是由17位当时称之为“轻量级方法学家”所编写签署的,他们的价值观是:我的与交互重于开发过程与工具;可用的软件重于复杂的文档;寻求客户的合做重于对合同谈判;对变化的响应重于始终遵循固定的计划。

  我的与交互重于开发过程与工具的缘由:一个由优秀的人员组成但使用普通的工具,要比使用优秀的工具但由普通人组成、紊乱的小组作得更好。多年来人们花了不少时间试图创建一种过程,以便把人看成机器上的一个能够替代的齿轮,但结果却并不成功。敏捷过程是认可每一个人都有特定的能力(以及缺点)对之加以利用,而不是把全部的人当成同样来看待。更重要的是,在这样的理念下,几个项目作下来,每一个人的能力都从中得以提升。这种人的能力的提升,对公司是无价之宝。而不至于把人当成齿轮,随着时间的推移,人的能力慢慢被消耗掉,最后变成留之无用、弃之惋惜的尴尬人物。

  可用的软件重于复杂的文档的缘由:可用的软件能够帮助开发人员在每次迭代结束的时候,得到一个稳定的、逐渐加强的版本。从而容许项目尽早开始,而且更为频繁的收集对产品和开发过程的反馈。随着每次迭代完成软件的增加,以保证开发小组始终是处理最有价值的功能,并且这些功能能够知足用户的期待。

  寻求客户的合做重于对合同的谈判的缘由:敏捷开发小组但愿与项目有关的全部团体都在朝共同方向努力,合同谈判有时会在一开始就使小组和客户出于争执中。敏捷开发追求的是要么你们一块儿赢,要么你们一块儿输。换句话说,就是但愿开发小组和客户在面对项目的时候,以一种合做的态度共同向目标前进。固然,合同是必需的,可是如何起草条款,每每影响到不一样的团体是进行合做式的仍是对抗式的努力。

  对变化的响应重于始终遵循固定的计划的缘由:敏捷开发认为对变化进行响应的价值重于始终遵循固定的计划。他们最终的焦点是向用户交付尽量多的价值。除了最简单的项目之外,用户不可能知道他们所须要的全部功能的每一个细节。不可避免地在过程当中会产生新的想法,也许今天看起来是必需的功能,明天就会以为不那么重要了。随着小组得到更多的知识和经验,他们的进展速度会比开始的时候指望值慢或者快。对敏捷开发来讲,一个计划是从某个角度对将来的见解,而具备多个不一样的角度看问题是有可能的。

[编辑]

 

项目的敏捷开发方法

  敏捷方法不少,包括 Scrum极限编程、功能驱动开发以及统一过程(RUP)等多种法,这些方法本质其实是同样的,敏捷开发小组主要的工做方式能够概括为:做为一个总体工做; 按短迭代周期工做; 每次迭代交付一些成果; 关注业务优先级; 检查与调整。下图是典型的敏捷过程总图,下面介绍其有关的特色。

  Image:敏捷过程总图.gif

  一、敏捷小组做为一个总体工做

  项目取得成功的关键在于,全部项目参与者都把本身当作朝向一个共同目标前进的团队的一员。“扔过去无论”的心理不是属于敏捷开发。设计师和架构师不会把程序设计“扔”给编码人员;编码人员也不会把只通过部分测试的代码“扔”给测试人员,一个成功的敏捷开发小组应该具备“咱们一块儿参与其中的思想”, “帮助他人完成目标”这个理念是敏捷开发的根本管理文化。固然,尽管强调一个总体,小组中应该有必定的角色分配,各类敏捷开发方法角色的起名方案可能不一样,希望则基本上是同样的。第一个角色是产品全部者,他的主要职责包括:确认小组成员都在追求一个共同的目标前景;肯定功能的优先等级,以便老是处理最有价值的功能;做出能够使项目的投入产生良好回报的决定。产品全部者一般是公司的市场部门或者产品管理部门的人员,在开发内部使用的软件的时候,产品全部者多是用户、用户的上级、分析师,也多是为项目提供资金的人。

  二、敏捷小组按短迭代周期工做

在敏捷项目中,整体上并无什么上游阶段、下游阶段,你能够根据须要定义开发过程在初始阶段能够有一个简短的分析、建模、设计,但只要项目真正开始,每次迭代都会作一样的工做(分析、设计、编码、测试。等等)。迭代是受时间框限制的,也就是说即便放弃一些功能,也必须结束迭代。时间框通常很短,大部分是 2~4周,在 Scrum中采用的是 30个日历天,也就是 4 周。迭代的时间长度通常是固定的,但也有报告说,有的小组在迭代开始的时候选择合适的时间长度。

  三、敏捷小组每次迭代交付一些成果

  比选择特定迭代长度更重要的,是开发小组在一次迭代中要把一个以上的不太精确的需求声明,通过分析、设计、编码、测试,变成可交付的软件(称之为功能增量)。固然并不须要把每次迭代的结果交付给用户,但目标是能够交付,这就意味着每次迭代都会增长一些小功能,但增长的每一个功能都要达到发布质量。每次迭代结束的时候让产品达到可交付状态十分重要,但这并不意味着要完成发布的所有工做,由于迭代的结果并非真正发布产品。假定一个小组须要在发布产品以前对软硬件进行为期两个月的“平均无端障时间”(MTBF)测试,他们不可能缩短这两个月的时间,但这个小组仍然是按照 4 周迭代,除了MTBF测试,其它都达到了发布状态。

  四、敏捷小组关注业务优先级

  敏捷开发小组从两个方面显示出他们对业务优先级的关注。首先,他们按照产品全部者制定的顺序交付功能,而产品全部者通常会按照组织在项目上的投资回报最大化的方式来肯定优先级,而且把它组织到产品发布中去。要达到这个目的,须要综合考虑开发小组的能力,以及所需功能的优先级来创建发布计划。在编写功能的时候,须要使工能的依赖性最小化。若是开发一个功能必须依赖其它 3 个功能,那产品全部者这就很难肯定功能优先级。功能彻底没有依赖是不太可能的,但把功能依赖性控制在最低程度仍是至关可行的。

  五、敏捷小组检查与调整

  任何项目开始的时候所创建的计划,仅仅是一个当前的猜想。有不少事情可让这样的计划失效:项目成员的增减,某种技术比预期的更好或更差,用户改变了想法,竞争者迫使咱们作出不一样的反应,等等。对此,敏捷小组不是惧怕这种变化,而是把这种变化当作使最终软件更好地反映实际须要的一个机会。每次新迭代开始,敏捷小组都会结合上一次迭代中得到新知识作出相应调整。若是认为一些因素可能会影响计划的准确性,也可能更改计划。好比发现某项工做比预计的更耗费时间,可能就会调整进展速度。也许,用户看到交付的产品后改变了想法,这就产生反馈,好比他发现他更但愿有另外一项功能,或者某个功能并不像先前看得那么重。经过先期发布增长更多的用户但愿的功能,或者减小某些低价值功能,就能够增长产品的价值。迭代开发是在变与不变中寻求平衡,在迭代开始的时候寻求变,而在迭代开发期间不能改变,以期集中精力完成已经肯定的工做。因为一次迭代的时间并不长,因此就使稳定性和易变性获得很好的平衡。在两次迭代期间改变优先级甚至功能自己,对于项目投资最大化是有益处的。从这个观点来看,迭代周期的长度选择就比较重要了,由于两次迭代之间是提供变动的机会,周期太长,变动机会就可能失去;周期过短,会发生频繁变动,并且分析、设计、编码、测试这些工做都不容易作到位。综合考虑,对于一个复杂项目,迭代周期选择4周仍是有道理的。

  MIT Sloan Management Review(麻省理工学院项目管理评论)所刊载的一篇为时两年对成功软件项目的研究报告,报告指出了软件项目得到成功的共同因素,排在首位的是迭代开发,而不是瀑布过程。其它的因素是:

  一、至少天天把新代码合并到整个系统,而且经过测试,对设计变动作出快速反应

  二、开发团队具有运做多个产品的工做经验。

  三、很早就致力于构建和提供内聚的架构。

  从这个报告中所透露出的信息告诉咱们,认真研究敏捷过程对软件项目的成功是很是有意义的,它的意义在于:

  1)给开发小组的自组织提供了机会

  经典项目管理就比如一个具有中央调度服务的航空管理系统,这个系统是自治的,并且是封闭的,但现实中更庞大的系统,彷佛并不属于中央调度控制系统,但也一样也是有效的。假如咱们开车到某个地方,咱们能够任意选择所须要的路线,咱们甚至不须要准确计算停车,只要咱们遵照交通法规,驾驶员能够临时根据路况改变某个转弯点,在驾驶游戏规则的框架内,依照自身最大利益作出决策。成千上万的驾驶者,并不须要中央控制和调度服务,人们仅仅在简单的交通法规的框架内,就能够完成综合起来看是更庞大的目标,不少事情从管理的角度只要抓住关键点,并不须要多么复杂的规则,每每会更有效。随着系统复杂度的提升,中央控制和调度系统面临崩溃。仔细研究交通系统的特色,咱们会发现这样的系统中独立的个体在一组适当的规则下运行,并不须要设计每一个个体临时变动的方案,而每一个个体只须要知道目标和大体的情况,他们彻底能够利用本身的聪明才智来决定本身的行为。

  2)缩短了反馈通道

  敏捷过程有效运做的另外一个缘由是,它极大的缩短了用户与开发者、预测目标与实施情况、投资与回报之间的反馈回路。在面对不断变化的市场、业务过程以及不断发展的技术状态的时候,便须要有一种方法在比较短的时间内发展完善。事实上,全部的过程改进都不一样程度的使用着戴明循环,以研究问题、测试解决方案、评估结果,进而根据已知的事实来进行改进,这就称之为基于事实的决策模式,咱们都知道,这比前端预测的决策方式更加有效。

  3)易于集思广益

  敏捷过程能有效应用的另外一个缘由在于,它能够就一个问题集思广益。咱们的经验告诉咱们当一个问题发生的时候,总有某些人员知道问题所在,但他的观点却遭到忽视。例如航天飞机在起飞阶段发生爆炸,过后分析出了各类缘由,但这种调查也提供给咱们一个惊人的事实,就是部分工程师早就意识到这些潜在问题,却没法说服他人重视这个担心。对这些事实的深刻思考,促使咱们研究咱们应该采起何种管理系统,使前线工做人员的经验、观点及担心获得充分的重视呢?

[编辑]

 

对敏捷开发的误解

  误解一:敏捷对人的要求很高

  不少人在尝试实施敏捷时说:敏捷对人的要求过高了,咱们没有这样的条件,咱们没有这样的人,所以咱们无法敏捷。但是,敏捷对人的要求真的那么高么? 软件归根到底仍是一种创造性活动,开发人员的技术水平和我的能力对软件的质量仍是起着决定性的做用,各类过程与方法只是帮助开发人员、测试人员等角色可以更好的合做,从而产生更高的生产力。无论用什么方法,开发人员的水平永远都是一个主要的因素。

  从另外一个角度来看:过程和方法究竟能帮开发人员多大忙?对于技术水平较低的开发人员,敏捷方法和传统方法对他的帮助是差很少的,所以看不到显着的效果,甚至有些时候还有反效果;而随着开发人员技术水平的提升,敏捷方法可以解开对人的束缚,鼓励创新,效果也会愈来愈显着。

  敏捷对人的要求并不高,并且会帮助你培养各类所需的能力,固然前提是你处在真正敏捷的环境中。

  误解二:敏捷没有文档,也不作设计

  这个误解从XP开始就没有中止过,XP鼓励“在非到必要且意义重大时不写文档”。这里面提到的“必要且意义重大”是一个判断标准,并非全部的文档都不写。例如,用户手册是否是“必要且意义重大”?这取决于客户的要求,若是客户不须要,那就不用写,若是客户须要,就必定要写;再如,架构设计文档要不要写?复杂要写,不复杂不用写。一般架构设计只须要比较简单的文档,对于有些项目,一幅简单的UML图就够了。所以,写不写,怎么写,都要根据这个文档到底有多大意义,产出和投入的比例,以及项目的具体状况决定。实际操做时可让项目组全部人员表决决定,尽可能避免由某一我的(好比lead)来决定。

  至于设计,XP奉行的是持续设计,并非不设计。这其实是将设计工做分摊到了天天的平常工做中,不断的设计、改善(重构),使得设计一直保持灵活可靠。至于编码前的预先设计,Kent Beck等人确实实行着不作任何预先设计的开发方式,可是对于咱们这些“非大师”级开发人员,必要的预先设计仍是须要的,只是不要太多,不要太细,要有未来会完全颠覆的准备。

  误解三:敏捷好,其余方法很差

  有些人一提到敏捷就大呼好,只要是敏捷的实践就什么都好,而提到CMMI等方法就大呼很差,无论是什么只要沾上边就哪里都很差,彷佛敏捷和其余方法是彻底对立的。牛顿说过,我是站在了巨人的肩膀上。敏捷一样也吸收了其余方法论的优势,也是站在了巨人的肩膀上,敏捷依然保持了不少历史悠久的实践和原则,只是表现方式不一样罢了。

  从另外一个方面来看,方法本没有好环,好与坏取决因而否适合解决你的问题。每一种方法都有他最善于解决的问题和最佳的发挥环境,在需求稳定、软件复杂度相对不高的时代,瀑布模型也能够工做的很好,而敏捷刚好适用于变化快风险高的项目 - 这偏偏是如今不少项目的共性。

  所以选择一个方法或过程,并非根据它是否敏捷,而应根据它是否适合。而要了解一个东西是否适合,仍是要尝试以后才知道,任何没有通过实践检验的东西都不可信。

  误解四:敏捷就是XP(极限编程),就是Scrum

  XP 和Scrum只是众多敏捷方法中的两种,还有不少其余的敏捷方法。龙生九子各个不一样,敏捷的这些方法看起来差异也是很大的,但是他们之因此被称为敏捷方法,就是由于他们背后的理念和原则都是相同的,这个原则就是《敏捷宣言》。学习敏捷不只仅要学习实践,还要理解实践后的原则,不只要理解怎么作,还要理解为何这么作,以及何时不要这么作。

  即便将XP或Scrum彻底的应用的你的项目中,也未见得就能成功,适合别人的东西未必就适合你。敏捷的这些实践和方法给了咱们一个起点,但绝对不是终点,最适合你的方式还要由你本身在实际工做中探索和寻找。

  误解五:敏捷很好,所以我要制定标准,全部项目都要遵循着个标准

  没有哪两个项目是同样的,客户是不同的,人员是不同的,需求是不同的,甚至没有什么多是同样的。不同的环境和问题,用一样的方法解决,是不可能解决的好的。方法是为人服务的,应该为项目团队找到最适合他们的方法,而不是先肯定方法,再让团队适应这个方法。所以也不存在适合全部项目的统一的方法。任何企图统一全部项目过程的方法都是不正确的。

  同时,对于同一个团队,随着项目的进行,对需求理解的深刻,对技术理解的深刻,一开始适合项目的过程和方法也会渐渐的不适合。这时候也须要团队对过程进行及时的调整,保证项目的质量和效率。敏捷是动态的,而非静止不变的,由于这个世界自己就是变化的,在变化的世界使用不变的方法,是不现实的。银弹历来就没有过,在有限的未来也不会存在。

相关文章
相关标签/搜索