关于软件工程:聊聊中后台产研一体化引子

「降本增效」是人们在生产过程中永恒不变的话题、永远的谋求——于公,短暂看能够让企业缩小开销并提供更为稳固、优质的产品;于私,可能使本人缩小反复无养分的劳动,将精力投入到更为「高精尖」的中央,有助于自我成长,为本人为企业发明更大更多的价值。 提效的形式当初想一下,在纯 Web 开发或大前端联合 Web 服务的畛域中,提效的形式都有什么? 单点提效从前端角度看,绝大部分前端团队都在不遗余力地去封装本人的工具库、UI 组件库、脚手架与构建工具,有些能力强点的团队还会封装利用开发框架、可视化源码搭建工具等。 从设计角度看,每个部门都会搞本人的设计规范/设计语言/设计体系,整顿出一份设计侧的 UI 组件库,并制订一套 Design Token 用于与其余设计及前端沟通交流和设计与研发之间的联动。 从后端角度看,貌似没有什么可提效的空间——后端语言大多公司用的是 Java,相干生态体系曾经很健全,顶多做些业务层面的封装。 从产品角度看,产品经理的工作就是接管/提出需要,做一些产品层面创收和改良相干的事件,这类思维流动为主的根本只能通过晋升思维能力去提效了,如果有个业务向的常识图谱兴许会好些。 链路提效同工种或者说分工内提效的天花板清晰可见,很容易就会达到瓶颈。要想更进一步,自然而然也必须要跳出本人所处角色的视角,横向寻求上下游间的买通,独特提效。 以前端为核心与其余环节进行买通的话,大略是这么几种伎俩:与设计之间是设计稿与前端代码互转,即 D2C、C2D;与产品之间是需要文档转代码,即 P2C;与后端之间是采纳 FaaS,即惯例意义的「前后端一体化」。 产研一体化上述几种链路提效形式的思考角度,个别都比拟表层,仍是以本人或别人的职能为出发点,而不是从问题的实质开始探究解决方案——尽管每个分工角色的交付物不同,但它们都应是同一样事物的体现。 那么,那个「同一样事物」是什么呢?是模型与流程,或是业务概念、概念之间的关系以及相互间的作用,又或是业务知识。 所以,链路级的提效最要害的一点就是畛域驱动的对立建模,其产物作为全链路的惟一可信起源(Single Source of Truth)。这意味着,从需要/产品、设计到开发、测试,都要基于同一份「数据」进行。 简要作业流程产品整顿各类需要,划分出各种业务概念,明确它们之间的关系和作用规定,这一过程就是在建模,最终会产出模型和流程。 建模完结后,产品能够在积淀了 UI 组件、逻辑函数等物料的利用搭建平台上联合建模的产物制作「原型」,「原型」即最终页面。 若已有物料中没有想要的 UI 组件和逻辑函数等,能够用占位符之类的形式标注下,让设计和开发去补上。而 UI 组件和逻辑函数等的研发,既能够走线下又可能走线上。 合作模式改革从下面的简要作业流程能够看出,从需要到研发最重要的角色根本只有产品和后端——产品负责领域建模和「原型」搭建,后端负责代码及数据连贯,设计和前端被「踢」了进来,业务研发流程失去了精简。 从另一方面来看,也应该去尽可能增员—— 软件开发过程就是从接到需要到产出合乎需要的可用软件的过程。在这一整个链条中,源头是需要提出方,而后通过产品、设计、开发、测试等不同岗位的人解决。 虽说源头是需求方,但更理论的源头是需求方的志愿。这个「志愿」是不是「真(true)」的,首先要打个问号。而后信息在传递过程中必定会有所损失,每个传递的节点能力越差损失得越多。 信息在每个人那里输出、输入时,因为常识、理解力、表达力等因素,多多少少都会产生变形,为了尽可能「保真」,必然的抉择就是缩小传递环节,也就是缩小参加人数,尽最大可能让需求方的志愿间接变成合乎需要的可用软件。 欧雷《说说「反混沌」:Hello, World!》 那设计和前端干嘛?要被裁了吗?!当然不是!尽管他们离业务比拟远,业务研发流程根本不须要他们,但利用搭建体系的物料开发和保护须要他们啊!在这里,他们对团队的价值可能最大化。 总结本文简略梳理了在纯 Web 开发或大前端联合 Web 服务的畛域中始终以来大家为提效所做的各种尝试,并描述了「产研一体化」在我脑中的轮廓。 目前次要是几个大厂以提效为目标在「产研一体化」方向进行摸索,我在这个方向上也有了比拟具体的有待尝试落地的想法,待日后缓缓道来。「反混沌」体系下的「Fxxk Design」和「Future.js」就是「产研一体化」这盘棋上的棋子。 「产研一体化」是中后盾利用低代码化过程的一部分,也是前端工业化过程的一部分。 本文其余浏览地址:集体网站|微信公众号

September 20, 2023 · 1 min · jiezi

关于软件工程:说说反混沌Fxxk-Design

某天,集结很多业内大牛的某厂间断开源了好几个前端相干我的项目,其中两个是 UI 组件库。嗬家伙!同时来俩,到底是想让人用哪个啊?居心想要逼死纠结星人的节奏? 那俩 UI 组件库的名字里都有「Design」,表明本人是「Design System」而不是一般的「UI Library」。这让我想起了那段时间一波又一波呈现的「元宇宙」公司。嗯~相熟的滋味。 不过,这也点了我一下——何不把我正在建设中与布局要做的 design-to-code 相干的我的项目一并打包成「Fxxk Design」呢?这样既有逼格又让人可能大略晓得我的那些货色是要解决哪些方面问题的。我这土鳖黑钢级直男码农终于学会了「概念包装」,真是谢谢它们了啊! 对我来说,那两个 UI 组件库简直没什么亮点,但各自又别离有一点引起了我的留神——其中一个提到的「Foundation + Adapter」模式和另一个将 UI 组件等独自发包打造物料市场的做法——这些与我在做和要做的事件非常贴近。 业界现状在说「Fxxk Design」之前,先来梳理下以后风行 UI 组件库的一些特点—— 最直观的就是,与某个技术栈进行了深度绑定,并以一整个 UI 组件汇合的模式提供给使用者。人们在交换时所用的语言形容是「React/Vue 的 UI 组件库 XXX」,而不是「XXX 组件」。 能够说,这是一种「单体架构」,如果某个 UI 组件新增了个性或修复了 bug,须要组件库整体降级,想要以组件粒度进行降级是不可能的。并且,就算是在雷同技术栈上,不同组件库间的无缝迁徙也是不存在的。 另外,那些 UI 组件库本身限死了端的状态——桌面端 UI 组件库、挪动端 UI 组件库。 以后风行的 UI 组件库,广泛定制能力较差,次要体现在两方面:没有格调变量或粒度不够,导致无奈定制格调或定制很无限;行为的定制也是同理,同时也是它们限死端的状态的起因之一。 因为定制能力差,再加上上文所述状况,不具备打造物料市场的条件,从而造成不了以它们为核心的生态系统。 它们的设计在我看来大多不够「原子」,不够「纯正」——如 Input 组件把本质上不是同一个货色的通过 type 属性去管制具体的展现状态;如 Button 组件领有值为 primary、text 等的 type 这种与其天然个性毫无关联的属性——这样的设计很容易让一个 UI 组件在多方面显得「臃肿」、「轻便」。 文档也千篇一律地列 API、放 demo,简直不会去具体地论述某个 UI 组件实用于哪些场景,有什么局限性——短少组件粒度的 UX/UI 设计模式等指导性内容。 还有一点比拟「国内特色」——提供面向中后盾场景的「Pro」。少数「Pro」是收费应用的,可就是有那么几个不仅品质不咋样,还须要购买受权才可能用。 Fxxk Design如文章结尾所说,「Fxxk Design」是将以 design-to-code 为指标的相干我的项目进行打包的「概念」,就像一个专门用来装书的箱子。 ...

September 19, 2023 · 1 min · jiezi

关于软件工程:我来聊聊前端应用表现层抽象

咱们处于变动很快的时代,无论是商业还是科技。一家公司看上去商业很胜利,兴许前脚刚上市,后脚就因为什么而退市,甚至开张;一项看似高大上的技术横空出世,各类媒体争先恐后地撰文介绍,热度炒得老高,没准没多久就呈现了竞争者、替代者。 在这样的大环境下,传统的「web 前端开发」演变成了「泛客户端开发」,前端开发者从「配置工程师」被「逼」成了「软件工程师」。开发变得更简单了,要解决的问题更多了,从业难度不知晋升了多少倍——前端早就不再简略。 在泛滥必须要解决的问题中的一个,就是体现层运行环境的兼容问题,像跨浏览器和跨端、平台、技术栈。留神,这里说的是「体现层」而不是「视图层」。 「体现层」与「视图层」「体现层」的英文是「presentation tier」或「presentation layer」,具体是哪个取决于是物理上还是逻辑上划分;而「视图层」的英文是「view」。「体现层」是「视图层」的超集,依据前端利用的架构设计,它们既能够不等又能够相等。 体现层「体现层」这个词出自经典的三层架构(或多层架构),是其中一个分层。三层架构包含数据层、逻辑层和体现层,个别用在 C/S 架构中。 为什么会在这篇讲前端开发的文章中提到它?这是因为,尽管在一些前端利用中用不到,尤其是快餐式利用,但在企业级简单前端利用中就非常须要一个前端的「三层架构」。 视图层「视图层」则来自体现层罕用的「model-view-whatever」模式中的「view」,即「视图」。至于说的时候在「视图」前面加个「层」字合不适合,就不在这里探讨了,文中皆应用「视图层」这个词。 运行环境兼容跨浏览器因为各浏览器厂商对规范实现的不统一以及浏览器的版本等起因,会导致个性反对不同、界面显示 bug 等问题的呈现。但庆幸的是,他们根本是依照规范来的,所以在开发时源码的语法简直没什么不同。 所谓的「跨浏览器」实际上就是利用浏览器额定的公有个性和技术或辅以 JS 对浏览器的 bug 进行「修改」与性能反对。 跨端、平台、技术栈当初,绝大部分的前端开发者是在做泛客户端开发——开发 web 利用、客户端利用和各类小程序。 在做 web 利用时须要思考 PC 端和挪动端是离开还是适配?技术选型是用 React、Vue?还是用 Web Components?或是用其余的?做客户端利用、各类小程序时这些也会面临技术选型的问题。 如果公司某个业务的性能笼罩了上述所有场景,该如何去撑持?与跨浏览器不同的是,不同端、平台、技术栈的源码语法不一样,要满足业务需要就得各开发一遍。然而,这显然老本过高,并且危险也有些大。 那么,要怎么解决这个问题呢?从源头登程。基本的源头是业务场景,而后是产品设计,但这些都不是开发人员可掌控的,简直无奈扭转。可能齐全被开发人员所左右的根本只有开发阶段的事件,那就从这个阶段的源头动手——源码编写。 若是与业务相干的代码只需编写一次就能运行在不同的端、平台、技术栈上,那真是太棒了!这将会大大地降低成本并缩小危险! 体现层的形象为了达到跨端、平台、技术栈的目标,须要将体现层再划分为形象层、运行层和适配层。其中,形象层是为了对立源码的编写形式,能够是 DSL、配置等,它是一种协定或约定;运行层就是须要被「跨」的端、平台、技术栈;适配层则是将形象层的产物转换为运行层失常运行所须要的模式。 体现层中能够被形象的大略有视图构造、组件外观、组件行为等。 视图构造在 web 前端开发中,HTML 就是一种视图构造的形象,形容了界面中都有什么,以及它们之间的层级关系。最终的显示须要浏览器解析 HTML 后调用操作系统的 GUI 工具库。 对于业务撑持来说,无论是 HTML 还是其余什么拼凑界面的形式,相对来说比拟低级(是「low level」而不是「low」),视图单元的划分粒度比拟细,在开发界面时就会破费更多的工夫。 咱们须要一种可能屏蔽一些不用关注的细节的视图构造形象,在这个形象中,每个视图单元都有着其在业务上的意义,而不是有没有都能够的角色。具体做法请看下文。 组件外观大部分已存在的组件的视觉出现是固定的,即某个组件的尺寸、形态、色彩、字体等无奈被定制。如果同样的交互只是因为视觉上有所差别就要从新写组件,或者在组件内部从新写份款式进行笼罩,那未免也太苦楚了…… 咱们能够将那些心愿可能被定制的视觉出现形象成「主题」的一部分,这部分能够被叫做「皮肤」。在进行定制时,分为线下和线上两种形式。 「线下」是指在利用部署前的开发阶段进行解决。在前端构建工具丰盛的当初,写页面款式时曾经不会去间接写 CSS,而是像 Sass 这种可编程式的预处理器。这样就能够抽取出一些管制视觉出现的 Sass 变量,须要定制时通过在内部对变量赋值进行笼罩,而不须要吃力重写组件或款式。 「线上」则是部署后依据运行时数据动静扭转。在皮肤定制即时预览和低代码平台等场景,是根本没机会去批改 Sass 变量并走一遍构建流程的,即便技术上可能办到。借助 CSS 自定义属性(CSS 变量)的力量能够较为不便地做到视觉出现的运行时变更。 组件行为组件除了外观,其行为也该当是能够定制的。看到「行为」这个词,第一反馈就是跟用户操作相干的事件,然而这里还包含与组件内部结构相干的。 对于组件的内部来说,组件外部就是个黑盒子,其本身构造的组成部分有的能够被上文所说的视图构造所管制,有的则无能为力: 上图是一个比较复杂的搜寻组件,尽管外观和布局看起来有所不同,但「它们」的确是同一个组件。外观不同的解决方案下面曾经大体阐明,这类视图构造无法控制的布局问题,须要枚举场景后在组件内进行反对,而后作为「主题」的一部分存在。 ...

September 9, 2023 · 3 min · jiezi

关于软件工程:我来聊聊模型驱动的前端开发

如果把「客户端」想成是楼,把「数据」想成是水——「Model」就是这幢楼的蓄水池,提供短缺的水源;「ViewModel」是将蓄水池里的水进行污染等加工的中央,而后输送给挨家挨户;「View」局部的每个 UI 组件就是「挨家挨户」,对水进行生产的中央。 所有皆为模型模型是人们依据事物特色将它们分类并形象后的后果,建模是人们认知世界的一种形式。 模型驱动数字世界这种虚拟空间,外面本无一物,是个须要被人开垦的充实的世界。那么人该如何打造数字世界呢? 就像《圣经》里形容的——上帝依照本人的样子发明了亚当这个世上第一个人类,又从他身上取下一根肋骨发明了夏娃这个世界上第二个人类。在这里,上帝将本人作为参照提取特色形象出祂所认为的「人」的模型,并依据这个模型发明出「亚当」和「夏娃」。 人在打造数字世界时必然会参照本人所存在的并且是本人所认知的世界,因为人不可能想像出本人无奈认知的事物。人们所形象的事实世界的事物的模型,就成了建设数字世界的根底,而数据则为结构数字世界的根本单元,数字世界成了事实世界的映射。 模型是数字世界万物的概念,程序是将概念具像化的工具,打造数字世界需从建模开始。 畛域驱动下面说了在打造数字世界时首先要建设模型,而后以模型为核心开始建造。那么要怎么进行建模呢? 至今为止,软件工程倒退这么多年,产生了很多方法论,其中「畛域驱动设计」在构建大型软件时是被宽泛驳回的实际办法。它的外围就是针对问题域剖析并建设畛域模型,理出模型间的关系及业务逻辑。 畛域驱动设计最罕用在商业层面的模型上,如:蕴含名称、编号、规格、出厂日期等信息的商品模型;同时也能够用在技术层面的模型上,如:蕴含名称、编码、字段、关系、束缚等用来形容模型的信息的模型。前者称之为「业务模型」,后者则是「元模型」。业务模型能够被元模型形容。 如果把模型映射为数据库表,那么元模型所对应的表中的每条记录都是元数据,业务模型所对应的表中的每条记录都是业务数据。 MVVM 架构规范的 MVVM 架构是 Model-View-ViewModel 三局部: 而这里所说的如下图所示: 从图中能够看到,多了个「Action」,所以实际上应该是 Model-View-ViewModel-Action 四局部。它们之间彼此拆散,以组合的形式协同工作。 为了考究对称美,将这种架构简称为「MVAVM」。 模型模型的主要职责是前、后端协定解决,以及对数据进行读写操作。 前、后端协定的解决包含元数据适配和 HTTP 申请结构。与后端对接的工作都管制在这一层,其余层的运作都基于这层适配后的后果。 在这层中进行读写的数据,既有业务数据又有元数据。元数据只加载一次,将适配后的后果进行缓存;业务数据只临时缓存尚未长久化的处于草稿状态的记录,长久化之后会将其删除。 ViewModelVM 的职责很单纯,就是解决业务数据流转相干的逻辑,即数据的散发、汇总与联动。实践上,在这层不间接进行任何与申请服务、执行动作相干的解决。 正如文章结尾所说——在一个利用中,数据是像水一样一直流动的,在此过程中,VM 应该起到铺设输送管线与在特定节点对数据进行解决的作用。依据这一特点,能够思考采纳管道和过滤器模式: 实例与数据的关系每个 VM 实例都来源于数据,是数据的变形,是具备能力的数据。 依据数据源的状态,VM 实例大抵分为列表、对象和值三种。如果值是布尔、数字、字符串等简略类型,那就即刻终止;若值为对象、列表等简单类型,则要递归上来,直到末端为简略类型。 须要留神的是,VM 实例与数据一一对应,其实质就是数据自身,而不是数据的容器。也就是说,VM 实例不是装水的瓶子,不能把曾经装的水倒掉换些水进来,而是一起抛弃。 生命周期任何对象的生命周期都可粗略地分为初始化、流动中与销毁三个阶段。 在初始化时依据策略获取本身数据源,与下级 VM 实例创立的流进行对接造成数据管道,而后创立向外推送本身变动的流。 流动期间就是一直地与外界进行数据交换: 视图输出变动时,通过对应的 VM 实例提交本身的数据变更在解决被提交的输出数据时会对其进行保留,并收回有数据提交的信号 本身的数据变动会通过数据管道流向上级 VM 实例内部(次要是下级)接管到信号后会做些后续解决销毁时做些清理、善后的工作,如:移除子 VM 援用,勾销订阅等。 数据流转在流动期间,数据在各层 VM 实例所连通的数据管道中流转时会发生变化,为了不便在不同场景下对数据进行解决,须要在初始化 VM 实例时将数据源进行备份,并生成几个拷贝:初始值(initial value)、默认值(default value)、原始值(data source)和以后值(current value)。 其中,初始值是获取到数据源那一刻的值,默认值在没有指定的状况下与初始值雷同,它们都是一经初始化就不会扭转的;以后值是本身一段时间内的数据变更,是最新的但不确定的值,能够了解为是一种草稿状态的值;原始值只有在下级以后值变动,接管到上级提交的数据或强制更新时才会更新,它是阶段性的确定值,能够看作是牢靠的数据。 「原始值」中的「原始」兴许会容易让人误会。在这里,它的含意是绝对于「以后值」来说,它是「原始」的,能够拿来作为参考的,而不是「最后的值」。表白「最后的值」的含意的是「初始值」。 原始值与以后值的区别与特点是: 原始值是确定的,以后值是不确定的;原始值是纯的,以后值是脏的;通过「提交(commit)」操作对各级的原始值、以后值进行同步;以后值的「版本」始终不落后于原始值;有些场景下原始值与以后值始终雷同。数据在流转时遵循以下几个准则: ...

September 8, 2023 · 2 min · jiezi

关于软件工程:我来聊聊配置驱动的视图开发

我在平时上下班开车时,全凭身材记忆与条件反射,根本不必脑子,所以脑子就空进去痴心妄想了,东想想西想想。 某天早上突然想到:最近几年,业界在开发时都考究以「数据驱动」的形式更新视图,回忆过来这几个月的工作内容,发现咱们的视图层开发并不是单纯的数据驱动,而是「配置驱动」。 视图更新让咱们先来回顾一下以往以及当初,在视图层开发时个别是如何更新视图的吧—— 在 React、Vue 等前端库/框架风行之前,根本以手动操作 DOM 的形式进行: <form> <div> <span>是否已婚</span> <div> <label><input type="radio" name="married" value="true"> 是</label> <label><input type="radio" name="married" value="false"> 否</label> </div> </div> <div id="childrenCountField" style="display: none;"> <label>孩子数量</label> <input type="text" name="childrenCount" value=""> </div></form><script>$('[name="married"]').on('change', function() { const $children = $('#childrenCountField'); if ($(this).val() === 'true') { $children.show(); } else { $children.hide(); }});</script>在 Vue 中应用的是数据绑定: <template> <el-form> <el-form-item label="是否已婚"> <el-radio-group v-model="married"> <el-radio :label="true">是</el-radio> <el-radio :label="false">否</el-radio> </el-radio-group> </el-form-item> <el-form-item label="孩子数量" v-show="married"> <el-input /> </el-form-item> </el-form></template><script>export default { data() { return { married: false }; }}</script>通过配置的形式来实现同样的事件: ...

September 5, 2023 · 2 min · jiezi

关于软件工程:工作轻松搞定感觉啥都会如何职场跃迁

工作轻松搞定,感觉啥都会?如何职场跃迁技术群聊天的时候,发现不同技术群或者集体也有过的一种景象:每日工作本人当初能够轻松拿捏,接下去如何破局?感觉工作内容也简略,仿佛没有很大的挑战性。我该如何解围,跃迁到职场或集体职业生涯下一等级? 遇到的另一个问题是,我的项目合作方面的问题我的项目内容很简略,感觉工作没挑战性 我的项目内容很简略,感觉工作没挑战性技术群聊天的时候,发现不同技术群或者集体也有过的一种景象:每日的工作内容,以本人当初的能力能够轻松拿捏,感觉没有挑战性,不好玩。集体能力倒退到这个阶段,如何破局、如何解围,跃迁到职场或集体职业生涯下一等级? 就像群里这个前端同学所说“前端我该学该搞的都搞的差不多了,还要怎么扩大?”。这仿佛是他当下的问题。开发个别分为业务侧开发、根底技术开发(也就是架构组)。各有优缺点,不做具体探讨。 做为一个业务同学,参加需要评审、出技术计划、画 UI、写动画、设计组件、测试、交付、没有任何问题了,然而业务同学倒退的肯定阶段,就应该思考底层技术或者工程化相干的货色。比方 CI、CD 打包构建优化、线上稳定性、页面秒开、首屏渲染时长的优化。说起优化,那必须要聊监控,要可度量,有数据撑持才不便聊到底优化了多少、优化了百分之多少,否则理性说“我这个很牛逼,优化了好多”那就不是工程师的该有的做事格调。要做前端监控就必须理解从地址栏输出一个 url 到整个页面渲染进去都做了什么事件,晓得浏览器工作原理才晓得问题症结在哪,才晓得具体如何做优化。然而很多写业务的同学不晓得或者只知其一;不知其二,很难系统化、全局剖析问题。那这个问题如何解决?那就是平时做货色之后,多问一步、多思考一步,为什么这么做、为什么这么设计?优缺点是什么?基于什么样的思考采取了目前的计划?该计划上线一段时间后去统计分析数据、复盘下符不合乎过后的预期,不是终极计划的话,要做什么样的调整。比方我就问了“tree-shaking”的原理是什么?ast 和 webpack 的一些 loader 如何工作的?可能就说不出来了。比方 React、JS、Weex、Vue、RN、Flutter 都有异样捕捉机制、捕捉之后如何还原出具体的案发现场,比方前端 js 打包就须要将 SourceMap 产物和版本号相关联做保留。后续不便符号化为原始数据。 根底技术也不是什么很神秘的货色。根底技术同学也有相似问题,感觉纯正的技术我的项目很乏味,但没啥问题、苦于降职。因为价值不够或者只是解决了某个单点问题,没有扩散到解决一类问题,没有推展到面。比方钻研出某个问题或者库,推广到不同业务线,宣讲接入落地。数据追踪并一直优化。缺的是价值闭环。缺的是业务 sense,可能技术上很赞,但业务同学不痛,或者不那么痛,接入的 ROI 不高。所以技术同学也要追踪业务问题,做到能解决理论业务问题(最好是很痛的业务问题)的技术我的项目。 所以平时应该多学多想多问为什、不设边界、不要只管好一亩三分地。如果只是做好本职工作,没有学“边界”之外的常识,没有当时储备好,要做某些事件可能连思路和一些可选项都没有。会比拟被动,相似于需要执行者,而不是需要或者技术我的项目开掘者 我的项目单干的痛写单个技术问题可能你很在行,然而我的项目写起来可能不那么棘手。 看起来你是在写程序,其实你做的是产品,那就不是简简单单的编程,无奈像刷Leetcode那样,刷一刷就熟了,而是要面对软件工程中的各种问题。 所以你面临的问题始终在变,大部分时候你不是在解决代码的问题,是在解决相似于:- 我怎么把需要形象成设计?- 我该抉择哪个技术计划?怎么找到最佳实际?- 这个技术、框架我没用过,怎么疾速用它实现我要的性能?- 这个Bug我该如何定位和修复?- 这个Bug是解决了,然而这段代码我怎么重构能力防止问题? 这外面其实最容易的反而是代码问题,要实现一个函数,搜寻一下可能他人曾经写好了,要解决一个Bug,用错误信息搜寻一下可能StackOverflow曾经有人解决过。 难的是你怎么把这些代码放在一起能满足你的需要,还能运行的高效,还要好保护,这些事不是ChatGPT或者AI短时间能代替的了的,须要很多年的积攒。 其实也没啥捷径,只能是投入工夫去一直地学习优良的代码,一直地实际,比方实现性能,重构代码。 可能在一个我的项目中,你本人的局部写的很棘手,然而多人合作,你无奈大展拳脚。有同学被我的项目合作方气死“遇到太菜的程序员队友,会被坑死”。可能是站在群里闲聊的一种话题,也可能是真的比拟有力吧,但呈现这个后果,有些起因是被动的,不可躲避,然而问题产生了,就须要躲避。呈现问题不可怕,继续呈现同一个问题(单点问题)、同一类问题(单点问题的解决能力拓展到面,问题形象剖析解决能力,可能是流程可能是机制) 任何我的项目,不论是互联网畛域的技术我的项目还是桥梁工程这种修建我的项目,最重要的是“过程治理”和“危险辨认”。kick-off 后规定好我的项目的几个要害节点,个别会从技术我的项目的参加同学中选定几个要害的 O,每日日会或者隔几天的我的项目站会(依据理论状况而定),须要同步我的项目进度、目前遇到的危险,须要依赖的外界因素是什么,失常吗?不失常的话,须要帮助什么资源,尽早干涉或者帮助。所以作为执行者,两头的一个角色,不要怄气,没啥用。 往往一个零碎一个我的项目是多个团队合作的,所以须要辨认上下游边界,对外该裸露什么能力或者提供什么接口(一句很相熟的话就是接口后行),协定先制订分明,依赖的节点是什么,各个工夫节点交付物是什么? 作为个体,我的项目中应该做做好本职工作,如果呈现危险,及时向要害的 O 同步问题。如果 O 不作为,本人能够被动推动上下游,或者向真正的项目经理同步问题裸露问题。要么遇到技术问题,本人有把握的话能够私下攻克,把危险给干掉。这些都是无效的。

August 23, 2023 · 1 min · jiezi

关于软件工程:什么是软件开发领域的-rollforward-发布策略

应用 roll-forward 办法,意味着只有最新版本的库才会取得谬误修复和新性能。 软件开发和公布畛域的 roll-forward 办法是一种基于版本控制的策略,其中只有最新版本的软件库或组件会被反对、更新和保护,旧版本则不再失去官网反对。这意味着在软件库或组件的更新过程中,只有最新版本能力取得 bug 修复和新个性的反对,而旧版本则被视为已过期和不受反对的。 在这种办法中,一旦公布了一个新版本,就会立刻进行对旧版本的反对和保护,而且所有的开发、测试和部署工作都将转移到新版本上。因而,roll-forward 办法通常可能帮忙开发团队更快地更新和改良软件库或组件,并缩小旧版本的保护老本,同时也能够促成用户更快地承受和适应新版本。 然而,这种办法也可能会导致兼容性问题,因为旧版本的应用程序可能会因为 API 和接口的变动而无奈与新版本的库或组件兼容。因而,在应用 roll-forward 办法时,须要确保软件库或组件的变动对应用程序的影响进行认真评估和测试,以防止潜在的问题。 以下是一些事实世界里驰名的应用 roll-forward 策略和不应用 roll-forward 策略进行公布的软件产品的例子: 应用 roll-forward 策略: Google Chrome 浏览器:Google Chrome 浏览器的开发团队采纳了 roll-forward 策略,只反对最新版本的浏览器,旧版本将不再取得反对和保护。React JavaScript 库:Facebook 的 React JavaScript 库也采纳了 roll-forward 策略,只反对最新版本的库,并激励用户及时更新以取得更好的性能和性能。Angular 框架:Angular 框架的开发团队也采纳了 roll-forward 策略,只反对最新版本的框架,并激励用户及时更新以取得更好的性能和性能。不应用 roll-forward 策略: Windows 操作系统:Windows 操作系统通常会提供长期反对版本和最新版本两种抉择,用户能够抉择长期反对版本取得更长时间的反对和保护。Ubuntu Linux 发行版:Ubuntu Linux 发行版也提供长期反对版本和规范版本两种抉择,用户能够依据本人的需要抉择适宜的版本。MySQL 数据库:MySQL 数据库提供长期反对版本和最新版本两种抉择,用户能够依据本人的需要抉择适宜的版本。

April 22, 2023 · 1 min · jiezi

关于软件工程:面向价值编程高ROI工程之旅

版本日期备注 1.02023.3.6文章首发0.前言在后面的系列文章中,我提到了相干的实践,实操,以及一段工作经验。在这篇文章中,我会用我本人和团队的经验来作为例子,诠释面向价值编程,并通过两个例子阐明高ROI工程的打造过程。 ROI个别指投资回报率。 是指通过投资而应返回的价值,即企业从一项投资流动中失去的经济回报。在这篇文章中,咱们指的是一个我的项目的投入产出比——当一个我的项目投入产出比高的时候,老板则会很乐意继续投入,相干人员也能够取得更高的报酬。反之则不然,甚至还会面临裁员危险。1. 初生牛犊不怕虎:刚好有个重构的机会刚到沃趣的时候,QPlus刚好在进行重构——起因是这个产品卖的还行,而其本质应关注数据库相干的业务,但理论开发时开发者须要关注底层根底施行的逻辑,而基础设施这块没有相干人员的储备。而我的到来刚好能够补救这点,我略懂一些Iaas,基于现有的开源我的项目也能够做出二次开发来满足业务需要。尽管咱们利用Iaas来疾速的满足业务需要,但在迭代过程中其复杂性也是须要咱们管制的。 之前在ZStack的时候研发和QA的配比是1:2。在我的项目的一开始,我就在团队里强调CleanCode和白盒测试的重要性——Iaas切实太简单了,一开始团队里就3个研发1个QA,咱们二开时如果不去刻意收敛它的复杂度,到前面的开发成本是收不住的,因而咱们须要通过自动化测试来保障正确性。但这在过后重构的时候带来了额定的老本——团队的同学不仅要去理解二开,还要做好CleanCode(因为CleanCode做不好,白盒测试是做不了的),这减慢了开发速度。过后公司里也呈现了不反对的声音——之前别的团队也没有搞过自动化,照样能迭代出产品,为什么你们肯定要搞自动化,搞的这么慢?这种状况下,整个团队压力特地大。 放在2018年的时候,国内公司广泛考究研发一把梭,梭上市场看成果。研发老本治理这个事根本不会提,堆不动就堆人。但我对此始终有不同的认识——如果咱们能够把老本降得更低,咱们的利润就会更高。而且这个行业怎么可能始终是夏天(不停的增长),总有遇到冬天的时候,这个时候ROI就特地的重要。万幸的是,咱们还是实现了重构,自动化的理念也在公司外部开始传开。再起初这个产品迭代得逐步成熟。当我在2022年的时候和共事聊起时,它曾经成了一个高ROI的我的项目,用两个人就能够撑持十分可观的销售额。 而对于ZStack二开、CleanCode和AutoTest,咱们在实践中也积攒出了一些教训。本着前人挖坑前人填坑的精力,我也是把相干的专栏列在这里: ZStack源码剖析:https://juejin.cn/column/6963644910666776612代码与技巧:https://juejin.cn/column/69647376837173575992. 盛年不再来,一日难再晨:一把梭的代价当咱们收回了新版的QPlus后,公司正在做一个新的产品线,次要是做数据同步相干的事,我对它十分感兴趣,便申请转过去了。 过后产品线曾经有了天使客户,落地成果以及利润也不错。所以想着寻找一些行业里的典型客户,成为行业解决方案后再在行业里复制开来。这个版本的版本号咱们定为2.0。过后的产品经理对迭代速度是有要求的,于是乎大家都热气腾腾的迭代,以至于大家review代码都要省着工夫——PM认为这事以后没有价值。同样的是咱们对于老框架的质疑,这让咱们的开发人员一次又一次的陷入底层细节,这也给前面的品质问题埋下了伏笔。 底层细节:诸如数据同步有误、位点失落等等等。咱们在应用Kafka与Storm时经常遇到这样的问题。这事再一次通知咱们——软件开发中的不可能三角是实在存在的:人力、品质、速度。当人力固定时,速度和品质只能二选一。 2.0前面迭代进去,落地到一半时,公司成立了新的产品线,从咱们这里抽调了一部分人走,再加上人员变动,当我作为主程时,研发起码的时候只有3集体。那是最难熬的时候,我要解决一堆2.0的问题,食了前人种的果。 起初随着业务机会的变多,咱们打算逐步进行v2版本的保护,去做v3版本的开发——这个版本次要是对v2版的技改,意在降本增效——通过框架的封装来防止开发陷入底层细节逻辑。再前面就是团队逐步扩招,研发扩招至7人,整个团队最多的时候有16集体。因为一开始我的项目是三跑的,v2的落地和v3的开发都要推动,v1的保护也要关注。前面咱们放弃了v2版本的落地,分心开始v3的迭代了。 v3版局部组件是齐全重写的,基于新框架,底层根底性能确实再也没有呈现过问。但管控平台局部沿用了之前的代码。因而仍有一系列品质相干问题需解决,如: 自动化测试在团队中已有相干实际,但大家不怎么乐意写,因为从短期来看这会减少集体工作量。但长期来看,这会减少软件的不稳定性。负责code review的同学,帮A同学review代码,这次review出了一类问题,下次A同学还是写出了这样的问题,review仅仅是查看,并没有让A同学成长,长期来看这部分工作量并没有收敛,写进去的代码也没什么晋升,间接带来品质危险。线上问题频繁呈现,但大家都感觉软件有问题是失常的。因而团队里的同学对于软件品质这块的关注是非常少的,但咱们以一个整体视角来看:一个bug从客户现场产生,驻场同学报告,报到PM,让QA复现,让研发跟进,这外面会有多少环沟通?又会有多少的细节在沟通中缺失?举个例子,有一次客户现场出了一个诡异的问题,咱们想把日志捞回来,得悉连机器的copy文件创建是xx点到yy点,当初曾经过了,因而要等今天才行。到了第二天,咱们拿到日志开始剖析,写好补丁本地验证,到了第三天公布过来,和客户沟通上线工夫,而后公布验证。这个case,一个bug花了3蠢才解决。但如果在外部发现,可能2小时就解决掉了。因而得出结论,一个bug被发现、修复的越早,带来的老本越小。因为问题频出,销售对于销售软件的信念和动向度也会逐步缩小, 长期来看不利于晋升产品的支出,几乎从本源上抹杀了产品倒退的可能。但如何压服老板去做一个品质治理,以及如何让老板看到过程中的成果、最终拿到后果,这是须要认真思考的——团队大了,开销也下来了,决策上的失误会让公司浪费资源,咱们应该尽量避免这样的事产生。 我认为,bug产生于开发期间,从它到客户现场被发现,两头还有许多环节,咱们应该激励事先发现,而不是预先救火。而那个时候业界里曾经有了很多成熟的计划,我在参考了许多计划后,做法如下: 关注稳定性:从写代码,到自测提交代码,到提测,到上线对整个软件生命周期进行关注,并量化跟踪考量。- 写代码时:关注代码标准扫描,设计文档与框架束缚- 自测提交代码时:关注自测覆盖率(白盒测试)以及代码review中review出的问题数- 提测时:关注千行代码bug率- 上线时:关注告警与重大问题统计,以及模型形象正当水平找适合的人来落地这些事:依据团队的梯队划分来赋予更多的权力和职责 对于职级高的同学,须要负责更多的模块,对相干模块的品质负责。品质好更利于绩效的评优对于倒退志愿强的同学,尝试给他额定的模块负责其品质整体的计划比较简单,并没有引入特地多的指标以及一系列的平台工具。数据的收集事通过人工来做的——这在团队规模较小时是可行的,这点也是思考到为了疾速落地。在施行以上计划时,团队每个月还会进行一次简略的谈话,和团队成员沟通相干的指标是否合乎预期,以及接下来的指标或不足之处等。通过了小半年的治理,整体的品质有了较大的晋升,团队里的成员也切实感触到了这套办法的可行性。 3. 小结以上两个例子和降本增效有着密切关系: 第一个例子中,取得的成绩是通过两个人能够撑持起可观的销售额。第二个例子中,取得的成绩是咱们能够将开发从繁琐细节、问题中解放出来,更好的反对业务性能迭代。同时咱们建设了数据思维,依据指标来判断咱们落地的后果,使品质问题长期来看处于收敛趋势。而数据思维让咱们的指标更加明确,也让咱们能够更好的去判断咱们是否有做好这件事、这件事是否有在好的方向倒退。而不是全凭一张嘴——这样将会很难说服众人,便无奈对齐这件事的价值。

March 17, 2023 · 1 min · jiezi

关于软件工程:内部开发者门户是什么

外部开发者门户(internal developer portal)是一个自助服务的应用程序和数据存储,能够为软件工程团队提供提供拜访所有软件组件、资源、环境、工具和文档的能力,让开发人员和管理人员跟踪并组织其工程团队构建和运行的所有内容。  信息碎片化问题经常困扰着运行简单分布式系统的软件工程组织,而外部开发者门户则旨在解决该问题。通过将开发人员所须要搜寻的信息,例如 wiki、代码仓库、配置文件、日志、指标等,放在一个集中的地位,从而防止在多个起源之间搜寻信息,为企业外部开发资产和流程提供实在牢靠的起源。  明天的文章将带你一起理解外部开发者门户的基本概念,包含其次要组成部分,特点以及劣势。  外部开发者门户的次要组成部分外部开发者门户形象了在不同的云环境上治理和记录应用程序的复杂性,通过自助式的利用和数据存储,让开发者和管理者可能拜访、跟踪和治理所有应用程序的资源和文档。外部开发者门户的次要组成部分会依据每个企业的具体需要和指标而有所区别,以下是咱们总结的一些常见的组成部分:  软件目录(software catalog):这是一个显示所有可用软件组件和资源的列表,比方应用程序、微服务、库、框架、数据库等。它能够帮忙开发者找到和反复利用现有的解决方案,而防止从头开始创立新的货色。评分卡层(scorecard layer):这是一个显示每个软件组件和资源的品质和可靠性的指标的界面,比方测试覆盖率、错误率、响应工夫等。它能够帮忙开发者抉择适合的组件和资源,并且可能及时发现并改良问题。自助服务操作层(developer self-service actions layer):这是一个可能让开发者本人执行一些常见工作而不须要其他人或团队帮忙的性能,比方创立新的微服务、配置基础设施、部署应用程序等。在这个性能的加持下,可能无效进步开发者效率和满意度,缩小谬误和提早。工作流自动化层(workflow automation layer):这是一个自动化地将代码从源代码仓库转移到生产环境或其余指标环境的过程。它能够帮忙开发者疾速地交付高质量和可靠性的软件产品,并且可能随时回滚或修复问题。内容仓库(content repository):内容仓库用来存储和展现软件开发生态系统的所有信息。包含微服务、利用、资源、文档、监控、部署等,以及这些信息的管理者和所有者。内容仓库能够应用版本控制系统,比方 Git 或 SVN。监控仪表盘(monitoring dashboard):监控仪表盘是一个显示软件系统中各种数据和指标的界面,比方日志、错误率、响应工夫等 。它能够帮忙开发者理解零碎运行状况,并且可能及时检测并解决问题。文档核心(documentation center):文档核心提供了所有相干文档,比方 API 参考文档、用户手册、教程等。它能够帮忙开发者学习和应用软件系统,并且可能放弃文档更新。 外部开发者门户的特点依据外部开发者门户的组成部分及其性能,咱们总结了以下几个要害特点:  可见性:外部开发者门户能够提供对软件生命周期的加强可见性,从设计到部署到监控。它能够显示所有可用的软件组件、资源、环境、工具和文档,以及它们是如何连贯的 。它还能够显示每个组件和资源的状态、健康状况和性能 。可追溯性:外部开发者门户能够提供对软件开发和交付过程的可追溯性。它能够跟踪并记录在整个生命周期中产生的所有变动、事件和行为 。它还能够链接并关联系统的不同元素,比方代码提交、配置文件、日志、指标等 。可审计性:外部开发者门户能够提供对软件开发和交付过程的可审计性。它能够确保并强制恪守最佳实际、规范和政策。还能够验证每个组件和资源的品质、安全性和可靠性。可察看性:外部开发者门户能够提供对软件开发和交付过程的可察看性。它能够收集并剖析来自各种起源的数据,比方日志、指标、追踪等。它还能够可视化并警报要害指标和异样。自助服务:外部开发者门户能够为开发者提供自助服务能力。它能够让开发者本人配置他们的基础设施和依赖,而不依赖于手动流程或内部团队。它还能够让开发者应用继续交付流水线部署并更新他们本人的应用程序。 外部开发者门户的劣势通过下面的内容,咱们总结出外部开发者门户可能帮忙企业的软件开发团队取得以下劣势:  进步生产力。开发者们能够轻松且疾速第找到他们所须要的资源,而无需再多个起源上搜寻或期待批准浪费时间。他们还能够应用预约义的模板和工作流来创立新微服务、配置环境、拜访云资源、执行数据工程操作等。加强合作。开发者能够与他们在团队和我的项目中的同行分享最佳实际、反馈、代码片段、文档和指标。他们还能够疾速找到现有服务和 API,以便重复使用或集成。提高质量。开发者能够遵循他们所做事件的最优门路,确保他们恪守组织设定的规范、指南和政策。他们还能够利用与外部开发者门户集成的自动化测试、监控和调试工具。升高危险。开发者能够通过应用外部开发者门户的验证输入输出来防止常见谬误,例如配置谬误、安全漏洞、数据失落或合规违规。如果出了问题,开发者也能够轻松地复原更改。 谁须要外部开发者门户?外部开发者门户通过提供一系列工具和资源来最大限度地反对开发团队,促成软件开发过程。这样看来外部开发者门户的确可能给企业软件工程团队带来许多益处,然而不是每个企业都须要它呢?事实上,施行外部开发者门户的决定该当基于组织的特定需要和指标。  例如,对于领有大型开发团队同时进行多个我的项目的组织,尤其是有简单、分布式、微服务化的软件系统企业,外部开发者门户能够帮忙简化开发过程并提高效率。通过在核心地位提供工具、资源和信息的便捷拜访,外部开发者门户能够为开发人员节省时间和精力。  相较而言,对于领有较少开发人员或我的项目较简略的较小企业组织,外部开发者门户可能不会提供太多价值。在这些状况下,应用现有工具和流程可能比投资于定制外部开发者门户更有理论效率。  总 结外部开发者门户可能解决分布式系统中的信息化碎片问题,并无效进步开发者的自主性和效率。然而,打造一套外部开发者门户是一个耗时且破费较高的过程,并不是所有企业都须要投资定制外部开发者门户,企业须要依据本身软件发开的需要以及我的项目的复杂度综合考量。

March 17, 2023 · 1 min · jiezi

关于软件工程:翻译什么造就了高级工程师编写程序-VS-构建系统

作者:Miłosz Piechocki 高级工程师关怀什么?他们关怀如何编写程序。他们最看重的是软件品质,采纳最佳实际,并尝试采纳最前沿的技术。他们投入了大量工夫去学习新技术。对他们来说,最终目标是编写出优雅、高性能、可保护的软件。 高级工程师关怀什么?他们关怀如何构建零碎。对他们来说,创立软件只是一系列流程中的一步。 第一步,他们质疑这个软件是否值得创立,这是首要的。他们会问,这个软件解决了什么问题,为何这些问题的解决很重要,谁会用这个软件以及用到什么水平。软件应该运行在哪里,以及如何监控它以确保它正确地运行。他们还会决定,如何掂量软件真的是在依照设计的要求去解决问题。构建零碎比建造软件的难度高多了,甚至到了一个不难受的水平。作为一个工程师,躲在本人的“小洞穴”中分心打磨那些小代码,是十分迷人的一件事。一般来说,咱们偏向于认为,业务的决定是产品经理的工作,代码的部署是运维团队的事件。然而,如果你参加到零碎构建的这些环节中来,将会带来微小的价值。因为你是最理解这个软件,以及应该如何运行、监控、扩大这个软件的人。还有,你的剖析能力、解决问题的技巧,让你的对于产品需要的洞察观点非常有价值。 技术上的专业知识当然十分重要。编写出优雅、高性能、可保护的软件,更容易运行,解体的频率更少,更容易扩张且须要更容易了解。然而,软件有可能解决了谬误的业务问题;或者客户因为性能缺点并不喜爱它,而你甚至因为没有没有监控到软件而不晓得这个事件。 零碎构建的流动一起来深刻地看看,这个零碎构建的流动步骤列表(并不详尽)。 制订需要。跟产品经理一起理清,要解决客户的什么问题,或者你会有一些如何用起码精力去实现工作的办法?制订非性能需要。通知产品经理一些非性能需要——零碎能包容多少用户,须要的性能、吞吐量、提早是什么?有没有平安和合法性上的顾虑?咱们要不要审核?规定的可用度是什么?打算迭代。和你的团队一起,制订一份履行打算,确保你制订了细小的、可行的进度治理。而后你就能尽快地递交成绩,跟产品经理确认里程碑了。制订内部支援。确保你搞清楚了所有的内部支援,跟你的项目经理或者团队沟通,为他们争取一些排期,并依据此来调整里程碑。测试。取决于你的公司运行形式,来决定你与团队或者品质团队的测试策略。协商好公布时候须要的品质阈值。(比方不能有未解决的重大问题,或者测试覆盖率要超过 X%)可观测性。决定好你要怎么监控零碎的健康状况,和设置解决产品问题的流程(比方团队值班)。用第三方计划(比方 SumoLogic)来设置监测器和仪表盘来实现这个需要吧。公布沟通。一旦你与团队和产品经理协商好了公布日期,请确保所有利益相干人都晓得这个事件。检查一下是不是有必要更新某些文档。总结我遇到过很多工程师,他们都深信职位降职的惟一办法,就是一直投入精力到专业技能上。当然这很重要,但惟一关系到你的公司的事件是,你能对业务营收产生多大的影响。把注意力从软件,转移到零碎上来吧。改善零碎比改善软件,更能让你回升到好的职位。

November 27, 2022 · 1 min · jiezi

关于软件工程:技术-|工程-浅谈开发中的逻辑可视化及-drawio-的自定义图形运用

事件是这样的,作为工程师,特地是全栈类的,常常要面对一人承当多角、关照多项的事实。 任何一个我的项目都会随着工夫倒退而逐步简单、精密和宏大化。在凝固纯正智力的编程开发过程中更是如此。 最近圈内很风行一个词:屎山。尽管听起来有些不雅,但却非常形象地比喻了随着开发进度倒退,而逐步繁杂、艰涩、不条理等等领有各种弊病的我的项目。 这种我的项目的代码,没有一个开发者违心碰,或者持续批改。就跟其名一样,唯恐避之不迭。 解决“屎山”惟一的方法,就是重整旗鼓,再造一个新我的项目(即使新我的项目也有倒退为新的“屎山”的可能)。 成熟的开发者通常领有肯定水平的代码洁癖,能够尽最大水平防止“屎山”的命运来临。但当我的项目体量增长后,再有洁癖的人,也会被各种逻辑搞到头晕。 不论是初学者还是资深开发,置信很多人都有这样的体验。第一天本人亲手写的代码,到了第二天再看的时候,就开始犯晕,到了第三天,感到了解艰难。静置一周后,就彻底不晓得本人过后是怎么写的了。如果放了超过半个月,可能连碰都不想碰了。 甚至经常会遇到,一顿饭的工夫,脑海中的逻辑运作就被彻彻底底打乱。 这与程序员的工作形式无关。智力输入须要大脑进入深度思考,优质高效的产出更是须要极为弱小的专一。这种状态下,对外界和工夫的感知都将削弱,也就是所谓的“忘我投入”(可参考心流实践)。 日常生活中大多不须要这种对脑力近乎到底的深刻,而程序员的工作则要求本人的大脑可能疾速进入状态。 但,光进入状态还不够。深度思考的目标是将逻辑以代码的模式编写进去,这个时候面对的问题就是:“逻辑”从哪里来,以及如何疾速将“逻辑”排汇到本人的大脑里。 先说“逻辑”从哪里来? 首先,开发不是零打碎敲的,少则数周,长则几十年。而人类是会忘记的,明天写的程序,特地是简单的算法,搁置一小会儿就会懵逼。这就须要咱们可能在文档或者代码中,从新载入/拾起之前的逻辑和状态。 在团队合作中,须要了解其他人写的代码是啥意思。集体开发中,则须要晓得本人之前写的是个啥。 这些代码或者文档的背地,就是“逻辑”。 做到准确无误的了解是根本要求,而事实的生产开发是个工程,谋求高效率就要求疾速精确了解。 如果把大脑类比为电脑,那么想要疾速进入深度状态,就要求你有一个优异的缓存,读写速度快,且容量大。 因为进入深度思考后,要同时顾及十分多的逻辑分支,大脑载荷会十分大。 而家喻户晓,计算机缓存的读写速度和容量大小,间接决定了性能好坏。人类大脑也是一样。 从“逻辑”连接角度看,咱们能够简略认为,编程工作须要将前序逻辑,加上本人的产出,输入给后续持续应用。就跟盖房子一样,理解后面的状态,增加新的状态,以供后来者持续添砖加瓦。 只不过这里所谓的砖瓦,具象为代码,实质是逻辑。也就是所谓的“搬砖”,搬本人或其他人大脑里生产的砖。 那读写速度由什么决定呢? 其实就是了解速度。 面对文档、代码,先了解字面意义,彻底消化吸收后,转化为形象逻辑,进而对逻辑进行加工生产,而后转化为代码和文档,再输入给将来的本人或者其余团队协作者。 下图是个繁难的示意,越往底走,跨层耗费的精力和脑力都越大。 这也是“屎山”为什么令人厌恶,就是因为要排汇的是一堆难以了解、繁杂艰涩的代码。不易浏览,且逻辑不通顺、不清晰、不条理,运行效率还低。对于谋求颅内低潮的程序员来说十分不敌对。 所以总有程序员之间会互骂对方写的代码跟“屎”一样,说的就是这个事。 优雅的代码总是给人一阵阵清风拂面的感觉。 进步了解速度有几个通过工夫考验的教训办法,比方好看的代码书写格调,规整的接口设计等等,常见的方法论有驼峰命名法这些。 还有就是好好写文档和正文,解释某一行要害代码是干啥用的。 规范的格局,通用的规定,体系的语言,对于升高了解老本非常无益。 此外,主观来讲,“了解”这个行为自身的状态,还与各种环境密切相关。 最近有一个显著的发现。工程体量大了当前,本人编程两个小时,有一个小时的工夫都用来了解回顾之前写的代码。而等到真正进入外围的编码过程中,最多也不过半小时。随着代码数的递增,了解难度和须要的工夫就会正相干增长。 更不用说,对于绝大多数开发者,还常常被外界乐音或者光线或者琐碎的杂事打乱。好不容易进入状态了,后果又被喊走解决其余事件,在进入深度思考的过程中重复横跳,耗费的是微小的精力。 我忽然了解了为什么之前会在一本业余书上看到作者举荐浏览《演员的自我涵养》。程序员进入逻辑世界的过程,就像是演员进入情感世界。试试如果在一个演员刚刚进入角色时马上把他喊出来,想要再次进入角色就会异样艰难。 同理于程序员,老是被打断,相当于从精力上覆灭。 这也是为啥简直所有的程序员都在早晨夜深人静后工作效率暴涨,完完全全没有打搅、能够宁静工作、彻底沉迷在编码过程中的大块残缺的工夫,在一天当中真的太少了。 而如果一周当中可能有一天齐全沉下心来解决一些重要节点,能够说对于任何一个开发者都是莫大的幸福。 (所以关爱程序员,请不要忽然吓他。) 既然环境不是那么的可控,那么咱们从人类如何了解问题这个最实质的角度登程,回归逻辑自身。 尽管轮子都是本人造的,编码的时候也极尽可能地放弃柔美,但还是不免被一些简单难点再次卡住。认知心理学通知咱们,人类对图像了解的速度远快于文本文字。所以用图像来形容逻辑,是一个十分无效的办法。 综上一大堆前置背景和现状条件,这就天然引申出一个概念:逻辑可视化。 比方常见的流程图,就是其中一种。 侥幸的是,通过工程学的长期倒退,前人总结出了一些方法论和无效的逻辑工具,其中最为驰名的,简直所有业余人员都应用过的,就是 UML,全称:对立建模语言。 首先,建模,不是单纯指物理层面的空间模型的构建,它能够指代构建任何设计或者概念中的实体,这些都能够叫做建模。比方数学模型、计算模型、软件模型等等等等,十分多。 UML 是一门语言,这就意味着它有零碎的形容问题的方法论。而承载这门语言的具体载体模式,是图形。换一步讲,就是 icon。 这就在逻辑、可视化和生产需要,三者之间构建起了桥梁。 而 UML 在很多大学里,都是一项专门的必修课。 狭义的 UML 能够泛指所有过程逻辑和流程。不过当初谈及,肯定离不开它是一种面向对象设计办法下的产物。 这就不得不提到,它的弊病。也是我集体当初开发过程中遇到的鸡肋的中央。 第一,UML 是文档驱动下的建模语言 置信说到文档驱动,第一反馈肯定是瀑布模型。而随着产品疾速迭代的需要和麻利开发的崛起,UML 这种规整老派的开发方式,无奈响应一直变动的需要。甚至逐步成为影响开发进度的绊脚石。 最传统的先建模,后依据模型来开发的工程思维,曾经跟不上当初的节奏了。所以目前来说,它的驱动作用逐步弱化,我集体更偏向于将其作为软件实现逻辑的演绎整顿工具。 第二,UML 是面向对象的 尽管想要整顿逻辑构造,但不论是用例图、时序图、泳道图、类图还是其余各种图模式,核心思想都是将操作环节看做对象的行为和交互。 面向对象的办法,很难将面向过程的局部也出现进去。但纯正的流程图形容下的面向过程思维又过于细颗粒度,对于想要在对象和过程之间找到一个适合的形容办法,UML 仿佛又太顶层了。 比如说,我想形容一个函数实现的嵌套关系。UML 既没有“函数图”这种货色,又没有必要将嵌套关系以流程图的形式完完全全铺开来看。 ...

December 31, 2021 · 2 min · jiezi

关于软件工程:ONES-解码为何数字化是超级工程

新冠疫情是数字化减速的一个标志性转折点。因为,咱们不是上网,而是活在了网上。 试想一下,如果没有互联网,没有快递、外卖,没有游戏、视频,没有社交平台,甚至没有在线健身,咱们怎么熬过那些从天而降的居家隔离日子?还有,近程办公、线上教学等的遍及让人们能够一再走出工作和学习的事实边界。 当疫情给许多事件按下暂停键时,却为数字化插上了高飞的翅膀。 接着,咱们持续诘问:推动数字化减速的背地硬核力量到底是什么? 越来越多的事实指向了一个答案:是遍布各行业热火朝天的软件研发工程,犹如百川汇海,独特驱使数字化快速前行——在这个意义上说,数字化就是一项宏大的超级软件工程。 研发管理工具公司 ONES 赋能于泛滥企业的软件开发工程,既参加了也见证了「以软件驱动数字化」的硬核时代过程,因此具备解码「数字化超级工程」底层逻辑的独特视角,也因而利用工程师思维将本人武装起来。 软件研发的工业化倒退 在搜索引擎上查找「超级工程」这个关键词,映入眼帘的既有高楼大桥,又有港口高铁;既有交通网络,又有粮食供应——都是看得见摸得着的、关系到国计民生的「巨无霸」零碎建设。 图片起源:Unsplash 例如,中国从无到有,建设了世界上最大的高速公路网络;架设了泛滥寰球技术难度最高的桥梁;建成了世界最长的高速铁路里程,它的长度甚至超过了寰球其余地区的总和;在中国的海岸线上,世界吞吐量排名前十的港口,就有七个位于中国。 这些都是原子世界的革新。与此同时,在比特世界里,也正在轰轰烈烈演出软件研发的「工程大戏」。咱们当初所享受到的数字化生存和工作上的各种便当,背地无一不来自大规模的软件研发工程。 现在,企业开发的软件,都不再是繁多的工具,而是一个零碎——将事实世界中的某一个场景,或者某些简单逻辑,落地成软件系统。也就是说,软件需要自身变简单了,须要大量的人力参加进来个体开发。 与此同时,因为编程语言的提高,程序员不须要再思考内存问题,不须要再面对垃圾回收、指针等「琐事」,程序员只有写逻辑就好了——这样一来,软件生产变得绝对容易。 于是,软件研发在制作上变得简略,而在治理上变得复杂。还有,人自身会有生物性局限,包含无限的表达能力、多人沟通的低效等方面。那么,在软件研发过程中如何进行对人的治理,就成为了一个大工程。 此前,在软件开发中,不少公司都可能落入误区,认为只有砸钱砸人,就无能成任何我的项目。也就是说,把做我的项目看成是一道简略算术题:如果某我的项目须要 12 集体月,那么 4 集体在 3 个月内能够竣工;如果把人手减少到 6 集体,那么 2 个月就能竣工,工期缩短 1/3。 然而,从事过软件开发工程的人都晓得,事实恰恰相反。后果是:减少的人手越多,我的项目进度越慢。因为,随着人越来越多,分工越来越细,流程越来越简单,人和人之间须要的沟通量会爆炸式增长,沟通破费的工夫比分工节俭的工夫还要多。 图片起源:Unsplash 因而,与路桥港口高铁等工程类似,当软件研发的底层结构设计实现后,须要大量的工程人员,通过大规模的零碎组织来执行施行——这是古代软件工业的关键点之一。 早在 2015 年,ONES 创始人兼 CEO 王颖奇就有了「软件工程化」趋势的认知预判。「我认为软件工程实际上会变成生产制造业,也就是说,软件业会成为“中国制作”的代表之一」,王颖奇说,软件研发不是科学研究,而是齐全工业化的工程畛域。 基于这个判断,王颖奇动摇了一个认知:软件研发须要好的管理工具。于是,他开办了企业级研发管理工具公司 ONES 。「我本人过来十几年都是在做工程治理,所以有一个十分清晰的认知就是:当一个软件研发团队的人数达到肯定规模,都须要业余的治理办法和管理工具」,王颖奇说,同时,因为本人的开创团队善于做软件,因而抉择了做产品技术门槛绝对高的研发治理方向。 正是有了系列的实际积攒,ONES 从而具备了察看数字化的工程师视角和思维。 工程师的结构化思维 美剧《生存大爆炸》的配角、蠢才科学家谢尔顿,明着说看不起本人的敌人霍华德。谢尔顿总批霍华德的工程师工作平铺直叙,一点创造性都没有,因为工程师是为了科学家的需要服务,而不是本人去发现。 以前,软件行业里的程序员被称为「科学家」;当初,程序员成为了软件工程师群体中的一员——软件工程师的定义囊括了产品经理、设计师、架构师等多方相干人士,能够说,软件工程是工程治理和综合治理伎俩的极限。 其实,并不是因为科学家智力更强或者程度更高,而是工程学的特点决定的。在这个意义上,能够回应《生存大爆炸》谢尔顿的是:工程师的专长不是发现,而是实现。 科学家次要的工作,是摸索「是什么」;而工程师思考的是另一方面,那就是「可能做什么」,在自然规律和其余因素限度的范畴内,摸索什么货色可能为人类带来理论的用处。 人们逐步达成了共识:科学家发现实在的世界,工程师实现一个可能的世界。 图片起源:Unsplash 而且,工程师思维超过了所谓的「工匠精力」。因为,工匠传承的是手艺,而工程师总是在思考怎么把手艺变成工艺——建设一套标准化的做法,升高人力参加的门槛,就是工艺。 「结构化或标准化,是工程师思维在数字化方面的典型体现」。ONES 联结创始人兼 CTO 冯斌说,结构化要做的是「清晰地定义所治理的对象」,例如文档这类非结构化的货色,是「糊」在一起的,很难抽取其中的数据。 「如果无奈用数字的形式将其表达出来,很难看分明其中详情,也没方法进行统计等性能」,在冯斌看来,依据 ONES 的客户实际,在团队合作的时候,非结构化的信息会让人抓瞎,因为无奈把握工作的完成度、工作的工夫安顿,以及不同团队之间的进度是否匹配,等等。「所以,结构化的首要指标是做到可视化,对所有治理的对象高深莫测,这是从混沌走向有序的开始」。 能够说,在没有构造的状况下,工程师从初步的概念和构想中,看到潜在的构造。即,不仅关注看得见的事物,也包含看不见的事物——工程师要思考零碎里各个元素,如何在逻辑、工夫、程序和性能方面进行连贯,剖析这些元素在什么条件下起作用,在什么条件下不起作用。 比方说,问卷调查显示,乘客的冀望是新飞机能更快达到目的地。那么,空气动力学家可能会认为,要解决的问题是怎么让飞机飞得更快,但工程师就会把整个旅程分成若干个组成部分,不仅要推敲航行的过程,还要钻研去机场、找停车位、定位航站楼、检票、托运行李、期待安检、候机以及达到最终目的地,等等多方面因素。 工程师就是这么操心,直至「结构化」呈现出井然有条。 简单软件研发 须要业余的管理工具 有个新编的老故事:面对一个装了半瓶水的瓶子,乐观主义者说,瓶子曾经半满了;悲观主义者说,唉,瓶子还有一半是空的。但工程师会说,这个瓶子其实没必要做这么大,只有一半大就够了。 这个故事是说工程师有个思维惯性叫「优化」——就是怎么能力多快好省地实现一个性能。 而优化的终点是工程师对「需要」的明确。能够说,一个简单的软件研发我的项目就像是一场接力赛跑,工程师往往是跑后半程的人。面对各方提出的需要,工程师依据需要实现接下来的工作,这个过程就像是传递接力棒。 在理论的软件工程中,这个交接棒的过程并不会一帆风顺,因为客户或者共事脑中的需要,可能是以含糊的一般语言造成的,而这一需要进入工程师脑中时,必须转化为数学和迷信的专门用语——最好的形式,就是固化到合作工具里的具体性能。 ONES 提供笼罩研发全流程的数字化治理 「2015 年守业以来,咱们只干了一件事,同时也构建了咱们的认知壁垒:就是认定只有波及软件都须要研发管理工具。当初回过头看,数字化减速让各种各样的公司里都建设了软件团队,而他们都须要工具——这些市场需求,反对咱们在过来几年里干对了事件」,王颖奇说,工程师思维的「需要导向」不仅落实到软件研发治理中,而且也利用到了 ONES 守业翻新的大思路里。 ...

December 17, 2021 · 1 min · jiezi

关于软件工程:ONES-X-蓝城兄弟|有机的研发管理改进是最健康的颠覆

社交利用是如何进行研发项目管理的? 蓝城兄弟始于 2000 年成立的集体网站“淡蓝色的回顾”,是国内最早,最具影响力的多元化社区之一。2012 年,网站创始人耿乐将网站挪动化,创建了基于地理位置的社交软件 Blued。目前,Blued 曾经累积了超过 5400 万用户,月沉闷用户(MAU)也达到了 600 万,笼罩寰球 210 个国家和地区。 2020 年,蓝城兄弟在美国纳斯达克上市,成为「粉红经济第一股」。依据其往年 11 月底颁布的三季报,旗下挪动利用月活用户达到 750 万;本季度总付费用户同比增长 57.1%至 77.6 万,实现了间断六个季度的持续增长。 那么,蓝城兄弟在研发项目管理中遇到了哪些痛点呢?又是如何克服困难的呢?本期 ONES《行业实际》带你理解蓝城兄弟的一站式研发项目管理。 客户背景作为一家主打社交的多元文化公司,蓝城兄弟始终致力于寻找最合适的研发管理工具和服务。 蓝城兄弟创始人耿乐曾示意:“打造产品力的外围是造成本人的飞轮效应,也就是要提供更好的用户体验,产品要做减法,服务要做加法,所有指标的达成归根到底还是产品力,如果没有好的产品,再好的团队,再好的组织构造都没有用。” 也就是说,在工具选型上,蓝城兄弟谋求的是适合的性能和高质量的服务。基于这样的认知,蓝城兄弟抉择了 ONES 。 随着蓝城兄弟实现对 lesdo、翻咔等公司的收买,以及赴美上市后,业务幅员继续拓展,于是研发团队也逐步扩充,这样一来,多产品线、多迭代的研发模式给公司带来了不小的挑战。 ONES 服务团队在对蓝城兄弟进行全面理解后,将其研发治理痛点梳理如下: 工具扩散,研发流程买通难业务线多,多我的项目进度把控难「治理」和「效率」关系均衡难ONES 研发治理解决方案针对蓝城兄弟的需要痛点,ONES 从以下几个方面登程,为其提供了残缺的解决方案。 标准流程,麻利开发在应用 ONES 之前,研发团队应用多种工具,团队外部交换次要依附邮件实现,工具与工具之间的数据和流程无奈买通,导致研发流程凌乱、数据割裂重大。此外,在需要治理上,团队须要收集跟版需要、非版本需要(即长期我的项目流动、需要变更)和技术优化需要,需要起源较为简单,现有的工具无奈进行无效的治理。 ONES 以「翻咔」我的项目为例,为蓝城兄弟搭建了一站式的研发项目管理解决方案,帮忙蓝城兄弟实现计划的落地和外部工具推广。首先,ONES 帮忙梳理实用于公司业务的麻利开发流程,其次,在大方向上,通过「翻咔」我的项目来治理翻咔的所有需要、技术优化、研发工作和 Bug,并通过迭代来承载每个版本的工作数据。将整个我的项目分为「需要阶段」、「研发阶段」、「测试阶段」和「灰度阶段」四个阶段,每个阶段设置具体的执行步骤,标准研发流程。 「翻咔」项目管理步骤 在需要治理上,ONES 为蓝城兄弟的三大需要起源布局了「创立需要字段阐明」,并且规定创立需要时,由产品经理创立需要单,由研发主管创立研发工作并关联相应需要,标准了需要提交的规范,从源头上解决问题。 除此之外,为了帮忙蓝城兄弟买通研发治理流程,ONES 服务团队依据不同的需要起源,梳理出了三套实用于不同需要的研发流程图,并进行了流程配置和字段阐明。使得研发团队可能疾速上手,麻利研发。 多我的项目总览,疾速把握进度因为蓝城兄弟旗下有多个产品和出海我的项目,产品研发须要涵盖 iOS、Android 多个操作系统,多产品线、多迭代的研发模式已成为常态,当并行我的项目一直增多,多我的项目的进度治理逐步变成了管理层头疼的问题。 ONES Plan 为其提供了管理者视角,帮忙他们实现了多我的项目的对立治理。在具体的施行中,通过将多个并行我的项目增加到同一个我的项目集中,管理者可从全局视角理解我的项目负责人、我的项目周期及我的项目数量等信息。 ONES Plan 我的项目集治理 随着我的项目的一直运行,各个我的项目的进度也会主动同步到 ONES Plan 中,管理者可通过甘特图直观把控多我的项目进度;对于须要重点关注的我的项目,也能够点击间接进入具体我的项目,查看我的项目详细信息。 ONES Plan 甘特图 实现治理与效率的均衡在此前的研发项目管理中,经常须要破费大量的工夫进行工具零碎的配置,加之团队成员须要常常手动进行工作项状态的更新和流转,节约了大量的工夫。蓝城兄弟迫切的寻求「治理与效率之间的均衡」。 在服务蓝城兄弟的过程中,ONES 首先为其理清了残缺的我的项目流程,使整个研发流程在同一个工具上跑通,团队成员们不用穿梭在多个工具之间,升高团队的单干老本,进步团队协同效率的同时,也突破了数据割裂的问题。 ...

December 9, 2021 · 1 min · jiezi

关于软件工程:QCon看点|亚马逊云科技可持续软件工程实践分享

在技术畛域里,2021 年是非凡的一年。这一年是亚马逊云科技成立的第 15 周年,这所有始于亚马逊云科技的对象存储解决方案 Amazon S3。在这过来的 15 年里,咱们能够看到云计算扭转了整个世界。并且有越来越多的客户将业务迁徙到私有云,开启了企业数字化之旅。 将来十年,云计算倒退将是一个继续扩张和一直迭代的过程。与此同时,“可继续倒退”已成为寰球、全国以及各个企业必须思考的主题之一。作为寰球当先的科技企业亚马逊云科技也在技术的可继续发展性上一直摸索,从基础设施到软件设计,有一整套自下而上的具备前瞻性的解决方案实现它。 作为亚马逊云科技可继续倒退架构副总裁,Adrian Cockcroft 在 9 月 11 日的亚马逊云科技中国峰会 Dev Day 上发表了主题演讲,解说了亚马逊云科技的可继续倒退策略,更重要的是,他从开发者的角度论述了亚马逊云科技如何进行可继续软件工程实际,咱们能够从中失去十分多的启发。 咱们为什么要关注“可继续倒退”可继续网络宣言:如果互联网是一个国家,那么它制作进去的二氧化碳排放量,排在寰球第七位。 联合国于 2015 年制订了一个寰球框架《巴黎协定》,随后各缔约国纷纷制订了“碳中和”门路和指标,对地球环境的衰弱倒退做出承诺。往年两会,中国也将“碳中和”和“碳达峰”写入政府工作报告,指标在2030年前实现“碳达峰”,2060 年前实现“碳中和”。毋庸置疑,可继续倒退曾经成为显而易见的社会共识。但在社会共识之下,还须要集体、企业、政府等各类社会主体的参加——其中体量宏大的科技企业是至关重要的参与者。 目前寰球互联网用户超过 46 亿,随着互联网普及率的回升,互联网很快将产生近 10亿吨二氧化碳,用电量相当于寰球的 10%。其中为数据中心供电所需的能源量大概每四年翻一番,就碳排放而言,ICT 行业自 2007 年以来始终奉献了 2-6%,简直与航空业持平。 好消息是,尽管 ICT 和云采纳呈指数级增长,但能源应用和碳排放却能绝对放弃不变,因为支流云提供商的超大规模数据中心正显著地提高效率。埃森哲的分析表明,假使采纳绿色办法迁徙至私有云,寰球二氧化碳排放量每年可缩小 5,900 万吨,这相当于动动手指就能缩小 2,200 万辆汽车的碳排放量! 在中国,互联网科技企业也都在一直加大力量投入到碳中和革新中。往年 8 月国内环保组织绿色战争 (Greenpeace) 公布了中国科技巨头《绿色云端 2021》排行榜,从能源信息披露、节能减碳体现、可再生能源方面合梳理了中国互联网科技企业的气象口头,相比去年,中国互联网科技企业整体均匀得分回升 11%。在 9 月 11 日的亚马逊云科技中国峰会 Dev Day 上,Adrian Cockcroft 示意亚马逊云科技获得的问题十分显著:亚马逊云科技的基础设施能源效率比一般美国企业数据中心高出 3.6 倍。同时,亚马逊云科技在执行雷同工作时,能够缩小 88% 的碳脚印。 这是多种因素促成的后果,Adrian Cockcroft讲述了亚马逊云科技摸索进去的构建绿色云服务的几条无效门路。 第一是水资源的爱护,亚马逊云科技应用蒸发冷却,循环用水,并尽可能在现场解决水。第二是洽购可再生能源,亚马逊云科技当初是美国和欧洲最大的可再生能源买家。第三是移除了传统的不间断电源(UPS),转而采纳了集成在每个机架的小型电池组合自定义电源。以往,每次在电压和直流电 / 交流电转换当中都会有一些功率损失,通过移除传统的 UPS,优化机架电源,缩小最终转换等措施让能量损失升高约 35%。第四是摸索翻新的服务器设计。中央处理器是古代计算机最耗电的局部,亚马逊云科技自研、基于ARM 架构的 Amazon Graviton 2 处理器每瓦特性能比其余业界规范流程高 2 ~ 3.5 倍。第五是在新数据中心建设中减少应用低碳混凝土,它可能缩小新修建碳排放量的25%。可继续软件工程实际很多人可能认为迁徙到云就足够了,以至于漠视了优化外部效率。实际上,迁徙到云上的每个工作负载都会耗费能源,有一些工作还尤其耗电,比方有计算密集的 AI 或 ML 业务。一项对自然语言解决模型的钻研阐明了问题的严重性,钻研表明训练一个 NLP 模型产生的碳排放量相当于从纽约到北京的航班往返 125 趟。 ...

October 21, 2021 · 1 min · jiezi

关于软件工程:作为软件工程师加入新团队时你需要先问这-20-个问题

不同的软件开发团队做事格调迥异,即便在企业外部,团队与团队之间也存在诸多差别。作为一名软件工程师,和新的搭档一起工作、开发新的软件通常是件令人兴奋的事件,同时他们还应思考很多问题。最近,软件工程师 Thomas Stringer 就从技术、合作、内部、产品多个角度进行了剖析。 技术1. 如何在本地构建软件?这是你应该学习的第一件事。毕竟,对于开发和运行软件来说,构建是第一步! 2. 如何在本地测试软件?CI pipeline 对于纠正测试谬误十分有用,同时它还能够缩短外部开发循环周期,确保测试顺利进行,同时查看回归。该 pipeline 不应成为创立或导致测试失败的首个迹象。 3. 如何设置开发环境?团队文档应对此有明确要求。此外你还应理解在开发机器上要应用哪些不同的工具,以便使本人成为团队的生产者。一次性设置好环境来解决 95% 的需要,要比在开始开发后遇到谬误和 gradle 依赖好得多。 4. 源代码在哪里?通常状况下,在新团队中你将在一个事后存在的代码库中工作。因而,你须要晓得代码在哪里,如何在本地机器上获取代码。 5. CI/CD pipeline 在哪里,它是如何工作的?心愿你能退出一个确保交付产品质量的团队。最常见的工具之一是 CI/CD pipeline。找出它的地位,并简略理解其工作原理,查看最近的一些运行,理解曾经进行的步骤。 6. 产品 backlog 在哪里?你面临的是软件的以后状态,但最好先理解其将来状态。疾速浏览 backlog,查看产品行将推出的一些优先事项。 7. 预生产和生产测试是如何进行的?新团队有集成环境吗?团队用 canary build 和部署来进行测试吗?团队是否引入混沌工程?你须要理解新团队如何确保其生产软件放弃在特定规范。 8. on-call 以什么模式进行?这款软件须要 on-call 吗?如果是,怎么轮换?事变产生频率是多少?on-call 是否有非工作工夫要求?当我执行 on-call 时,如何失去告诉?通常在你退出新团队时不会立即开始 on-call 轮换,因而随着工夫的推移,你能够在执行 on-call 前失去一些答案。 9. 外部文档在哪里?新团队在哪里保护外部文档?是最新版吗? 合作10. 团队中的每个人在关注什么?软件团队通常有多名工程师,理解团队中不同程序员的关注点是不错的做法。 11. 团队每周的节奏是怎么的?有每日站立会议吗?须要每周签到(weekly check-in)吗?你须要理解新团队的 “典型” 一周是什么样子。 12. “初学者”问题该向谁发问?退出新团队后,你通常会被调配一个“入职搭档”——一个晓得事件如何运作的团队老人。这是一件十分有价值的事件,尤其是在你对新软件简直无所不知、提出的问题十分高级的状况下。这很失常,提出初学者问题并不丢人,即便你是高级工程师。 13. 谁来驱动新性能?这款产品是否有产品经理?团队中有架构师与工程师协同工作吗?你须要理解个性申请的上游源头。如果能抽出工夫和这个人(或这些人)理解产品的近期和远期前景就更好了。 14. 团队如何沟通?新团队应用 Slack 或者 Teams 吗?还是大部分异步通信通过电子邮件实现?工程师们通常终日都在议论问题或进行其余类型的探讨。作为团队中的新成员,你须要理解这些沟通渠道。 内部15. 如何取得客户反馈?这是 GitHub 上的开源软件吗?GitHubissue 是咱们取得反馈的形式吗?还是有销售团队作为从客户到产品团队的代理人?咱们能够从不同的反对团队处收集常见的客户痛点吗?换句话说,你须要理解新团队如何取得用户反馈,无论是通过另一个平台、集体还是团队。毕竟,咱们是为用户编写软件的。 ...

July 23, 2021 · 1 min · jiezi

关于软件工程:构建之法现代软件工程读书笔记二

请问戴维.帕纳斯( David Lorge Parnas 软件工程专家) 学生: 您认为未来会有什么令人兴奋的软件工程技术呈现吗? 戴维·帕纳斯: 最有用的技术不在未来,而是曾经呈现好些年了,只不过咱们没好好用。 很多学生学了一些编程语言,读了一些技术博客,个别都豪情万丈。他们做一个我的项目巴不得展示本人平生所学。 再加上前沿技术,做一个轰动的翻新。这诚然值得激励,不过实际表明,这些往往都不能胜利。 咱们来看下胜利的例子,他们是怎么做的,例如Linux刚开发的时候: I'm doing a (free) operating system(just a hobby, won't be big and professional like gnu) for 386(486) AT clones。 我正在为 386(486) AT clones 编写一个操作系统(只是一个业务喜好而已,没有GNU那么业余和宏大)。 管理学巨匠彼得·德鲁克 : Those entrepreneurs who start out with the idea that they'll make it big - can be guaranteed failure. 那些一开始就认为本人会做大的企业家必定会失败。 前言开始本篇的时候,我想起我的初中,我的初中是在镇上念的,一周回去一次,我总是信念满满的指定了一个指标,回家把我背的书都看一遍,而后每次我都把所有的书都背了回去。然而你晓得小孩子经常抵挡不了引诱,比方睡懒觉,玩游戏。当我睡醒的时候,我的小伙伴就来了,而后咱们就去打游戏。再上学的时候,我就把这些书在背到学校。这种重复性工作应该是继续了我的初中时代。想来那个时候,背回来的书一本没看的理由就是我制订的指标太过宏大,让我感觉很难实现,然而那个时候的我显然没有意识到这一点,每次周末,我将书桌中的书全副装进书包的时候,我都是满心欢喜,空想着本人在家里看书会让家里人开心。 我又想起我上大学的我的项目较量,我的项目组长想做一个美妆社区商城,定位上大抵相等于小红书和淘宝的结合体,介绍一下咱们过后的技术背景: Servlet、JSP、JQuery、MySQL(根本SQL语句的编写),过后刚学完这些,信念爆棚。但过后有没有实现小红书加淘宝的结合体的设计指标呢! 应该是没有实现的,大抵相当于咱们的指标是建一栋楼,最初建了一个风雨飘摇的茅草屋,只等"八月秋高风怒号",就“卷我屋上三重茅”。 我想假使指标太过宏大,总会让人产生莫名的畏惧心理,惯例的做法就是将宏大的指标拆解为若干个看起来容易实现的小指标。 我想解决大问题诚然让人感觉美好,然而把小问题真正解决好,也不容易。 浅谈软件设计准则人们在实践中碰到的需要是常常变动的,软件设计的许多准则是从实际而来,这些准则正是为了在一直变动的需要中保障程序的可维护性和效率。咱们以两个软件设计准则为例,第一,繁多职责准则(Single Responsibility Principle,SRP)指出: 一个模块(类)应该是只有一个导致它变动的起因,一个模块应该齐全对某个性能负责。软件设计的经典著作《麻利软件开发:准则、模式、实际》分下上面的例子: 一个解决正方形的模块有两个性能: ① 计算面积 ② 画出这个正方形。这个设计让一个模块负责两个不同的职责: 进行几何运算(与显示图形无关)和图形界面绘出正方形。如果一个汇合计算的程序须要应用这个模块,那么它就须要同时包含图形显示的局部(因为是在同一个模块中),这是一种节约,同时引入了不必要的依赖(因为图形显示和图形底层实现相干),障碍了可移植性。另外,几何计算需要的扭转和图形显示需要的扭转都会导致这个模块产生的变动,减少谬误产生的危险。 ...

June 14, 2021 · 1 min · jiezi

关于软件工程:构建之法现代软件工程读书笔记一

前言聊聊大学期间学习的《软件工程导论》吧,长这个样子: 刚上这门课的时候,我上课是很认真的,我很致力的去听课去学习,然而我发现我对书上的这些UML办法、麻利开发流程啊,有一点了解,但如同又悬浮在我四周。于是在学了一个月之后,我就开始翻起了我所感兴趣的书籍,有的时候是玩手机。课程完结之后,我感觉如同学到了一些货色,比方UML、软件工程开发模式(瀑布开发、麻利)、ER、面向对象五个根本准则等。然而我感觉又是什么都没学到,随着这门课的完结,这些概念缓缓的从我的脑袋缓缓中淡去,随着编码的变多,我开始扫视我的代码,以下问题呈现在我的脑海: 面向对象的五个根本准则该如何取舍,这五个根本准则是无条件要恪守的吗?该如何对待咱们的软件?那些软件开发模式又是什么?该如何掂量一个软件工程师?UML有那么重要吗?设计软件该如何设计?设计一个框架、一个库、一个应用型软件的不同在什么中央?这兴许就应该是软件工程答复的问题 ,但为什么我过后学习《软件工程导论》的没有这种感觉呢? 兴许是过后的代码量比拟少吧,我在上《软件工程导论》的时候,还没尝试构建过一个小型的我的项目,兴许是教学方式的问题,这门课的授课形式还是那种老师在下面讲书上的概念,相似于语文课的模式,老师是经验过软件开发的,然而过后的咱们没有合作开发过,兴许对”软件”有一点了解了,但此时对于工程还没有领会。兴许《软件工程导论》这门课自身就应该是在实践中学习(learning in doing)的课程。 我心愿失去以上问题的答案,于是我打算重学软件工程,然而我并不想再用《软件工程导论》这门教材,我在豆瓣中发现了另一本软件工程的教材《构建之法》,我大抵试看了几章,感觉这本书能答复下面我提出的问题,于是我就买了下来,认真读了一下发现还有意外播种,现将读书笔记分享给诸君,心愿对诸君会有所帮忙。 该如何掂量一个软件工程师?往年我换了工作,也经验将近十几场面试,我是一名Java后端工程师,所以面试的次要技术点如下: 汇合: LinkedList ArrayList CopyOnWriteList HashMap ConcurrentHashMap框架: Spring Spring MVC Spring Cloud Spring Boot MyBatis数据结构与算法: 排序算法、二叉树计算机网络: UDP、TCP、HTTP、HTTPS、WebSocket数据库: 索引、SQL优化、事务、事务的隔离级别JVM: 垃圾回收算法、垃圾回收器多线程: 线程池 CountDownLatch 锁面试的根本流程个别是: 口试->技术面(可能是几面)->HR面。面试官面试的办法大多都是问答题模式,有的是看了我的博客和冀望薪资问的特地细节往偏了问,而有的则是想到哪问到哪,也有一些让我感觉比拟有意思的面试,逐层深刻。面试之后我就在思考这么一个问题,这样的形式面试是对的吗?这样就可能掂量一个软件工程师吗? 我之前加过一些技术群,看到了一些应届生的面大厂的状况,大厂仿佛也是这么个面试办法,问答题。大厂是可能引领技术风潮的,我在跟他们交换的时候,仿佛普遍认为搞搞分布式、算法和数据结构、设计模式、源码,这些是最能掂量一个软件工程师。这也造成了一个循环圈,大厂面这些技术点,而后各个技术视频讲如何答。那这些是对的吗? 这样的形式仿佛从我毕业开始面试就是这样,问了之前教训比拟丰盛的同时,仿佛三年前的面试也是这样,从来如此,便对么。 那我问我本人如果让你去面试呢? 你会如何面试一个人,你会如何问呢? 或者更进一步如何掂量一个软件工程师呢? 问: 你的职业是软件工程师吗? 答: 是 问: 你感觉你的”职业”到哪一水平? 答: 嗯,我在一个能发工资的中央下班,靠我的软件技术挣钱,所以我相当的职业。 问: 像职业篮球队员那样职业? 答: 差不多吧。 问: 职业篮球队员都有很具体的记录阐明,例如,上面的表格阐明了NBA职业篮球远动员的赛场体现: 图表显示了队员出场次数、首发、工夫、投篮、命中率等。作为一个职业软件工程师,你有相似的数据阐明你所有的职业流动和问题么? 答: 嗯…… 没有。。惟一的数据是我的”上场工夫”还是挺长的,而且常常打加时赛—加班。 要用图表来掂量一个软件工程师仿佛有点艰难,软件工程师从事的工作仿佛更为简单一点,那如何掂量一个软件工程师呢? 我认为能够从以下几个方向去掂量,或者软件工程师能够思考从以下几个方面去成长: 积攒软件开发相干的常识,晋升技术技能(如对具体技术的把握,入手能力)。积攒问题畛域的常识和教训(例如: 对游戏、医疗和金融行业的理解) 第一点和第二点在简历上大多都能够看失去,也能够比拟容易的检测进去,随着教训的增长,一个工程师能够把握更宽泛、更深刻的技术和问题畛域的常识。 对通用的软件设计思维和软件工程思维的了解 这一方面就比拟虚,什么是好的软件设计思维? 什么是好的软件工程思维? 一个工程师开了博客,转发了很多他人的文章,折算有思维吗? 另一个工程师保持做任何设计都要画UML图,这算有思维吗? 晋升职业技能(区别于技术技能) 职业技能包含: 自我管理的能力,表白和交换的能力,与人单干的能力,按质按量实现工作的执行力,这些能力在IT行业和其余行业都很重要。理论成绩绝大部分软件工程师的工作成绩都是能够公开的,你参加的产品用户评估如何?市场占有率如何? 对用户有多大的价值。 你在其中起了什么作用?行胜于言,这些理论工作成绩,是最重要的评估规范。我目前浅显的认识是绝大多数软件工程都会抉择第一个方面去成长,残余几个方面大多没人会想,也很少会有人去想到。 ...

June 6, 2021 · 1 min · jiezi

关于软件工程:CMMI-V20丨如何通过CMMI真正在企业中的实施规模化敏捷开发

在过来的几年中,麻利开发曾经从一个利基概念(利基(niche)是指针对企业的劣势细分进去的市场,这个市场不大,而且没有失去令人满意的服务。产品推动这个市场,有盈利的根底。)转变为寰球许多大公司采纳的规范实际。 通过小型、自我管理的团队减速软件开发现已成为一种公认的策略,并且越来越被视为企业翻新和竞争力的要害。CMMI研究院的统计报告显示,2018年加入CMMI评估的企业80%以上应用了麻利。现在,随着公司寻求更多地将敏捷性注入整个组织及其文化中,麻利技术曾经不仅仅利用于软件开发畛域。只管麻利越来越风行,然而当企业尝试在整个企业范畴内推广应用麻利软件开发时,依然会遇到问题。只管麻利对于小型、独立、自我管理的我的项目可能十分无效,然而很难用于协调构建大型、简单的产品和零碎所需的多个我的项目和团队。后果就是公司遇到了与晚期软件开发办法雷同的许多辣手的问题,例如集成和接口问题、未能充沛满足所有需要、提早交付和品质缺点。 因而,随着麻利的遍及,对克服上述问题的最佳实际的需要也在一直增长。CMMI V2.0提供了这些最佳实际,可帮忙组织建设成熟的流程,来管制规模化麻利可能面对的简单状况和危险。 CMMI V2.0如何帮忙实现规模化麻利CMMI是一套用于改善业务性能的最佳实际。多年来,很多公司曾经同时应用了CMMI和麻利开发。 2017年的一项考察发现,应用CMMI的公司中有80%也应用麻利。然而最新版本的CMMI V2.0加强了两者之间的协同作用,为在麻利开发中建设规模和弹性提供了间接领导。 CMMI V2.0专门解决了企业在尝试规模化麻利时遇到的挑战,例如精确估算开发工夫度量和资源、集成系统组件以及放弃品质。CMMI V2.0还反对对胜利施行至关重要的各种其它流程,例如治理和交付服务以及抉择和治理供应商流程。此外,CMMI V2.0还扩大笼罩到包含安全性在内的更多畛域。CMMI V2.0不仅着重于进步绩效,而且着眼于维持习惯和持久性,以确保企业随着工夫的推移放弃该性能。CMMI V2.0在最小化投入的同时,提供了这些要害劣势,因为CMMI V2.0容许抉择满足业务独特需要的实际域。 全面应用CMMI是胜利施行规模化麻利开发的要害,这与试图大规模反对麻利的其它办法造成鲜明对比。通常,这些办法解决了一些挑战,却齐全无奈解决其它挑战。SAFe(规模化麻利框架)就是一个例子,它在要害畛域短少要害因素,例如软件品质、设计和集成、治理服务和供应商、布局和管理工作、治理业务弹性以及维持性能。 解决集成问题来看看CMMI是如何帮忙组织胜利地利用规模化麻利开发。组织常常遇到麻烦的两个畛域是我的项目估算和产品集成。CMMI提供了牢靠的估算办法,这些估算办法反对用许多小组件构建大型简单零碎的麻利办法。它还能够帮忙确保设计的每个零碎组件能够与其余组件集成。 在大多数组织中,多个团队在Sprint中开发零碎的组件。大型零碎可能波及许多独自的Sprint,每个冲刺都会生成必须集成的组件。麻利我的项目通常在设计和需要阶段无奈充沛解决这一问题,后果就是许多软件开发组织遇到了与接口和组件之间的集成相干的重大问题。如果您有两个开发团队进行麻利冲刺,生产不同的组件,那么您如何晓得这些组件将在冲刺实现后是否能够集成?如果您尚未事后定义组件的组装形式,那么每个组件都将各自在真空中被独立构建。 CMMI提供了弱小的框架帮忙公司在初始需要和设计阶段定义接口和集成需要,而后在整个开发过程中的各个冲刺里进行跟踪和测试。如果没有CMMI,确保无故障集成的能力则齐全取决于团队的教训。专家级开发人员可能具备远见卓识和专业知识来确保组件可能进行集成。然而经验不足的人可能不足要害常识,即便他们可能疾速编写良好的代码。CMMI的最佳实际从根本上进步了团队的专业知识,使团队可能发现本来可能会脱漏的潜在问题。 通过反对重要但惯例的我的项目工作(如估算和集成),CMMI使开发人员能够将精力集中在他们真正应该做的事件上,从而解决了开发新性能带来的艰巨而乏味的挑战。而且,因为CMMI为所有开发我的项目提供了通用框架,因而也使在我的项目之间的人员调动变得更加容易,进步了组织的敏捷性。随着一个我的项目的完结,CMMI使这些开发人员更轻松地转向另一个我的项目并开始工作。 应用CMMI防止麻利凌乱如果没有成熟的流程来协调多个团队和集体进行冲刺,那么规模化麻利开发的尝试很容易导致凌乱。CMMI提供了可在整个组织中应用的全面而独特的业务性能框架,因而公司能够更好地协调我的项目、集成简单的零碎,更快地交付更高质量的软件。 参考文献:How to Truly Scale Agile Development in the Enterprise—with CMMI,Submitted by: CMMI Institute, 15 October, 2019https://cmmiinstitute.com/res...

May 21, 2021 · 1 min · jiezi

关于软件工程:得物技术软件工程与PlantUML实战

前言正如任何生物一样,软件也有孕育,诞生,成长,成熟以及兴起的生命过程,常称为“软件生命周期”。软件生命周期个别分为几个阶段:既制订打算、需要剖析、设计、编码、测试、运行和保护。而UML则反对从需要剖析到设计再到编码的过程。 需要剖析和设计占了整个软件生命周期的两个局部,可见其重要性,而很多时候,开发同学经常会跳过这两步,间接进入编码阶段。本文次要应用PlantUML开源我的项目,联合一些理论我的项目中的需要进行剖析和设计。 PlantUML是一种简略易懂的UML图形绘制语言,几行代码就能够绘制出各种UML图。在纯熟之后,能够比个别的绘图工具高效许多。更重要的一点是便于版本治理,在一直迭代的性能需要中,能够继续保护。 需要剖析-前奏前奏,是一个首歌的基调,肯定水平上决定了整首歌的格调变动。需要剖析是整个软件设计的根底。有很多开发同学会有疑难:需要剖析是产品经理要干的事件啊?关咱们开发什么事件?其实不然,需要剖析对于开发来说,首要也是重要的目标,就是精确并且简洁的答复“谁用什么零碎做什么事”。咱们通常能够应用「用例图」来搞清楚这一问题。 用例图例如在「晒单有礼」这个我的项目中,有如下用例图: “客户端用户应用晒单有礼零碎匹配晒单策略”“经营人员应用该零碎设置晒单策略”PlantUML代码 @startuml left to right direction actor 经营人员 as D actor 客户端用户 as user rectangle 晒单有礼(精简版) { D --> (晒单策略):设置 user --> (晒单) (晒单) --> (晒单策略):匹配 } @enduml 解析 1、@staruml 和 @enduml plantuml预发的起始和完结标识2、left to right direction //标识图形由左向右绘制 3、actor 用户(君子图形) 4、rectangle 矩形框,外部代码图形都在这个框内 5、 --> 实线箭头 上图简略的表白了,“客户端用户应用晒单有礼零碎匹配晒单策略”和“经营人员应用该零碎设置晒单策略”,曾经能能大略答复“谁用什么零碎做什么事”了。然而还不够精密,咱们还能够做如下扩大: 上图将“晒单”和“晒单策略”进行了补充和解释。 “晒单”入口来源于订单列表“晒单策略”分为“设置”和“匹配”两个动作“晒单”包含“发动静”和“匹配晒单策略”“设置晒单策略”包含“设置激励类型”和“设置画像”PlantUML代码 @startuml left to right direction actor 经营人员 as D actor 客户端用户 as user rectangle 晒单有礼(扩大版) { D --> (设置晒单策略) (设置晒单策略) .> (设置画像):《include》 ...

May 7, 2021 · 3 min · jiezi

关于项目管理:带你全面认识CMMI-V20终实施落地

引入CMMI的办法一共有四个阶段将您的业务过程和最佳实际最终交融在一起,并在该范畴内从新发明整个组织的“实现形式”。这四个阶段是: 策略摸索:此阶段的重点是理解以后状态并打算过渡到所需状态。摸索阶段的目标是缩小或打消我的项目期间的危险,通过防止代价昂扬的谬误来节省时间和金钱。典型的流动包含打算会议、入职培训、进行差距剖析、确定工作范畴、制作书面调查结果文件、具体阐明优劣势以及理论状态与打算(或冀望)状态之间的差距。而后将这些摸索后果用于制订我的项目打算,该打算概述了业务需要、技术需要、工作、时间表和要害里程碑。 过程开发:在打算阶段实现之后,过程开发开始。典型的流动包含:● 确定并定义政策、打算、过程、手册、程序和工作指导书;● 记录业务过程、输出和输入;● 成立一个具备预约角色和职责的领导委员会。 新过程施行:过程的施行将策略和打算转化为口头;领导员工;设定目标、度量和指标; 对人员进行对于新的要求的培训并监控其总体有效性。 验证:最初一个阶段评估零碎的有效性可确保所有上述条件均可承受并能够应用。规范工作包含测试、评估性能、评估数据、剖析报告和审核。 确定降级点的执行发起人十分有用,也很重要,这包含辨认过程所有者、展现治理承诺、尽早确定存储库和工具,并建设沟通渠道。 最初,我的项目的胜利始于打算的好坏,以及有效性的监控和与所有公司员工的沟通。 CMMI 落地的办法 每家企业都有两个过程, 一个是书面的文档化的过程,一个是组织及我的项目外面理论执行的过程。很可怜的是,许多通过了CMMI三级甚至更高级别的企业,这两个过程是不统一的。如果不能保障制订的过程须遵循一句话——说到做到,做不到则不说。这句话看似简略,做起来却并不容易。 真正做到言行不一、CMMI落地须要在以下几个方面下功夫:1.建设可用合乎我的项目特点,并具备肯定灵活性的规范过程。 组织规范过程的起源次要有两个:一个是组织外部的无效最佳实际。将这些实际纳入规范非常重要,它们代表企业本身的工程治理精髓;另一个是可用的业界最佳实际及规范,本地化后纳入到规范过程中。如果要确保过程能在组织外部达到制度化、日常化的执行力度,在建设过程时,肯定要思考的企业以后的现状及约束条件。2.建设机制,定期欠缺批改过程 。 过程执行者不能用过程中的缺点作为不执行的借口,但他们都负有改良的责任,因为只有他们通过应用过程,真正晓得过程的有余在哪里。让组织过程在执行过程中不断完善就须要让过程改良制度化、日常化。国内企业常有这样一种状况:所有的过程批改都是为评估触发。有些企业通过了三级,在做四级评估的时候,我看不到任何二、三级相干过程的欠缺批改记录。这就是说,在3年的工夫里,这些过程没有变过,可是认真评估过后,发现有很多改良机会。依据我的教训,没有改良(改变)过的过程,很有可能是没有在我的项目中真正被应用的。但咱们肯定要让这些欠缺工作简略,不麻烦!3.用过程执行者相熟的语言及形式形容过程。 很多企业喜爱用CMMI中的语言形容过程,造成很大的培训老本及沟通的阻碍。一个过程看起来在任何一家企业都能够用,它往往是一个很难执行的过程。4.建设机制,束缚违反过程的状况产生。 很多企业都建设了过程QA机制,在我的项目及组织中进行过程合乎的稽核。如何建设企业外部无效的QA机制,至今依然是个值得钻研的课题。在很多企业中,不执行明确定义的过程是没有什么结果的。后果导向,要让过程执行者看到过程的成果及过程改良的价值。 CMMI存在的根底大家置信这样的过程公理:产品的品质和用来开发这个产品的过程的品质有极大的关系。让过程执行者忠诚执行组织定义的过程,须要让他们看到过程及过程改良的益处:看到品质的晋升,看到效率的晋升,看到客户的认可。只有让管理者及工程人员服气组织制订的过程是我的项目胜利的重要保障,那么这些规范过程才会真正让大家承受。5.过程治理中,要留神组织、我的项目、集体的均衡。 如果治理的天平太偏向于组织,会使得我的项目及集体短少必要的灵便从而丢失能源。如果走到另一个极其,只思考个体性、灵活性,则会给组织带来危险,失去学习的机会。从久远来讲也不能保证质量及生产效率的继续晋升。 在导入CMMI时,国内企业犯的最常见的谬误是将它当成一个过程、一个规范,而不是一个模型。看一看CMMI中的原话:“CMMI既不包含过程(process)也不包含程序流程(procedure)。”思考到各类组织,各类我的项目的微小差别,谁也无奈制订一个涵盖所有企业、我的项目的规范过程,CMMI当然也不是这样一个规范过程。CMMI只是形容了无效过程的特色,给出了必须实现的指标以及实现这些指标倡议做的事。

April 13, 2021 · 1 min · jiezi

关于软件工程:软件工程-总结各种coupling和cohesion

coupling和cohesion都是依照从好到坏排序的 对于好的software design,应该有较高的cohesion和较低的coupling. 5个coupling:data coupling 共享原子数据stamp coupling 共享简单数据结构(其实只用到了数据结构的一小部分)control coupling 一个给另一个传参数 调用被调用模块的一小部分common coupling 都可能写全局变量content coupling 一个模块间接援用另一个模块7个cohesion:information cohesion 每个流动(activity)都有独立代码 都在同一个数据结构上操作functional cohesion 模块外面的所有流动都为了同一个task或者functioncommunicational cohesion 模块中两个流动因为某个流程而互相关联 且操作同一个数据结构(e.g. 更新数据库信息并把数据库信息发送到打印机)procedural cohesion 两个流动因为某个流程而互相关联temporal cohesion 流动因为时序而互相关联logical cohesion 模块中的流动是逻辑上而不是性能上相干coincidental cohesion 模块外面有的性能不相干

March 21, 2021 · 1 min · jiezi

关于软件工程:软件工程-白盒测试各种覆盖详解

最近在温习软工明天在这里总结一下白盒测试的各种笼罩~ 从覆盖度高到覆盖度低的排序:1.Path coverage(门路笼罩)2.Combinatory coverage(多重条件笼罩/组合笼罩)3.Clause/Branch coverage(条件/判断笼罩)4.Clause coverage(条件笼罩)5.Branch coverage(判断笼罩)6.Statement coverage(语句笼罩)用一个例子来示范: 门路笼罩-path coverage对于门路笼罩,要把每一条路的每一种组合都走一遍。在这里我标记了可能呈现分叉的abcdef几条路,对于门路笼罩应该把以下门路的状况都走一遍:acefbcefacdfbcdf 多重条件笼罩/组合笼罩 combinatory coverage每一个判断中的每一个子句的组合都要笼罩 第一个判断:x>3 and z<10 x>3z<10x>3 and z<101TTT2TFF3FTF4FFF第二个判断 x==4 or y>5 x==4y>5x==4 or y>51TTT2TFF3FTF4FFF一组测试用例:(经测验你会发现能够满足全副的下面8个状况)1) {x=4,y=6,z=5} 2) {x=4,y=3,z=10} 3) {x=3,y=4,z=5}4) {x=3,y=6,z=11} 条件/判断笼罩条件笼罩 clause coverage每一个判断中的每个子句的不同true false都要取一次 对于这里一共有四个子句:x>3 z<10 x==4 y>5x>3 取true false各一次(以及以上) z<10取true false各一次(以及以上)...以此类推 就能够满足条件笼罩 一组测试用例: {x=4, y=5, z=5}{x=3, y=6, z=15}判断笼罩 branch coverage如图上标记,每个判断之后都有T和F的后果。 判断笼罩则是在可能在每个判断取至多一个T和至多一次F的测试用例笼罩。 一组测试用例: {x=4, y=5, z=5}{x=2, y=5, z=5}

March 21, 2021 · 1 min · jiezi

关于软件工程:软件工程期末总结

Software EngineeringChapter1:introsoftware=computer programs + associated documentationsoftware we need methods to develope high-qualified software: standardsystematicefficientdependableeasy-to-usesoftware engineering is an discipline that is concerned with all aspects of software production from initial conception to operation and maintenance.History of software engineering:SE's composition: software development(needs methods, techniques and tools to support) requirements engineeringsoftware designcodingtestingmaintenanceproject managementstructured and object-orientedsoftware engineering ethics confidentialitycompetenceintellectual property rightscomputer misuseChapter2:software process modelOrganization of processes and activities Key points in this chapter: ...

March 19, 2021 · 6 min · jiezi

关于软件工程:翻译软件设计的哲学21-复杂性的定义

For the purposes of this book, I define “complexity” in a practical way. Complexity is anything related to the structure of a software system that makes it hard to understand and modify the system. Complexity can take many forms. For example, it might be hard to understand how a piece of code works; it might take a lot of effort to implement a small improvement, or it might not be clear which parts of the system must be modified to make the improvement; it might be difficult to fix one bug without introducing another. If a software system is hard to understand and modify, then it is complicated; if it is easy to understand and modify, then it is simple. ...

February 27, 2021 · 3 min · jiezi

关于软件工程:翻译软件设计的哲学2-复杂度的本质

Chapter 2 The Nature of Complexity 第 2 章 复杂度的实质This book is about how to design software systems to minimize their complexity. The first step is to understand the enemy. Exactly what is “complexity”? How can you tell if a system is unnecessarily complex? What causes systems to become complex? This chapter will address those questions at a high level; subsequent chapters will show you how to recognize complexity at a lower level, in terms of specific structural features. ...

February 23, 2021 · 2 min · jiezi

关于软件工程:翻译软件设计的哲学1-介绍一切都是关于复杂度

Writing computer software is one of the purest creative activities in the history of the human race. Programmers aren’t bound by practical limitations such as the laws of physics; we can create exciting virtual worlds with behaviors that could never exist in the real world. Programming doesn’t require great physical skill or coordination, like ballet or basketball. All programming requires is a creative mind and the ability to organize your thoughts. If you can visualize a system, you can probably implement it in a computer program. ...

February 18, 2021 · 6 min · jiezi

关于软件工程:软件工程抽象泄漏与编程

什么是形象透露这个概念来自于 Joel Spolsky 的博客(The Law of Leaky Abstractions – Joel on Software)。文章大略讲述了,从 TCP 协定的封装让 IP 协定变得稳固牢靠,推导出“形象封装能够失去优良的设计”,再到如果数据传输不再稳固,那就使用者就不得不深刻底层(甚至到物理层,查看是不是宠物蛇咬断了网线)去排除问题,总结出“形象封装总是会透露的,咱们不得不破费更多的精力,并学习更多的常识,能力排除这个问题”。 举个更简略的例子,咱们要出一趟远门,最底层的办法,就是用脚走。这时候,咱们拿出一个优良的形象——一辆宝马汽车,它把轮子、座位、引擎等等概念封装起来,给了咱们简略的应用办法(开车、转弯、停车等),让这趟旅途快捷舒服。然而,它总有一天会呈现形象透露——一个整机的损坏导致抛锚了,这时候咱们就不得不找到相熟整个汽车零碎的工程师去解决这个问题。因为咱们没有对于这个高级形象的常识,只管解决形式是简略的“替换一个 xx 整机”。 古代世界基于形象运行,形象让咱们的生存极为便捷。比方“去公司”就是,地铁公司把这趟路程和布局封装起来了,你只须要刷 2 次卡就行了,不须要晓得它的运作原理。然而一旦形象呈现问题,某天某种原因地铁停运了,解决问题就须要大量且零碎的常识,去查看所有的细节。 对编程的影响当初对前端最大的误会是,懂一个 MVC 框架,例如 Vue,就能够进行开发工作了。Vue 把 HTML、JS 和 CSS 封装成了固定构造的文件,繁冗的 DOM 绑定和操作形象成了简略的数据赋值。那是不是意味着,看一下文档而后跑一下 TodoList demo 就能够干活了? 当然不是。后面说到了,形象肯定存在透露。按钮须要消抖、组件嵌套不能冒泡,这些状况一旦呈现,咱们就不得不回到 timer 线程、事件机制这些底层常识的学习。甚至 Vue 的原理,例如数组绑定后不更新了、如何实现长按指令的场景,会逼迫咱们学习它的零碎机制。 后果就是,只管形象封装越来越高级,然而学习编程仍不见得变得简略。 启发形象能让咱们的生存变得便当。越来越多的高级工具会呈现,节约掉繁冗的细节工作,让开发变得疾速。咱们必须把握形象的外部机制,和底层的原理常识,能力应答形象透露。更多、更高级的形象,让调试和保护变得艰难。形象让分工变得明确。前后端难以调换,全栈工程师也会变得稀缺。形象透露导致的常识老本,让编程工作易学难精的水平加剧。

February 5, 2021 · 1 min · jiezi

关于软件工程:软件工程开发之道了解能力和复杂度是前提

摘要:软件工程须要哪些能力以及如何保障这些能力?哪些地方咱们须要留神复杂度的问题?小引在本文中咱们将探讨如下问题: 1. 软件工程须要哪些能力以及如何保障这些能力? 2. 哪些地方咱们须要留神复杂度的问题? 3. 考试的目标是什么? 4. 莫要让标准解放了咱们的手脚,成为技术的奴隶。 5. 要让人的能力施展到极致,良好的心情是必须要有的。 6. 专一于本人善于的事件。那么,在软件工程当中,这样的理念应该如何贯彻呢? 7. 为什么咱们须要对代码和设计进行重构?如何做? 8. 如何保障软件开发的品质呢? 能力能力是成败的要害,这一节咱们会探讨一下软件工程须要哪些能力以及如何保障这些能力。 所谓软件工程能力实际上就是解决具体问题的能力,也就是把理论中的问题转化成我的项目代码的能力。 说一下人员能力的晋升这一块儿。一个我的项目中肯定要有一个灵魂式的人物。只管咱们说当初的软件工程开发是一个团队的单干成绩,然而这个团队中必须要有一个大脑,不能有多个大脑。 这个怎么了解呢?对于小的团队来说,假如有10集体的团队,那咱们就说组长就是这个团队的灵魂。组长须要率领大家进行调研工作,最初作出论断进行取舍。这中央能够了解为架构设计方向的制订。 这一步看清楚当前,接下来就须要把这些活儿调配给各个成员。组长须要严密跟进我的项目的停顿,比如说遇到难题了,组长须要跟成员一起去解决掉,而不是交给成员去独自攻克。 如果没有难题,成员独自解决了,那么组长须要把解决方案了解透彻,把好关,同时好好学习。 对于组长的要求是假如整个团队10集体,只剩下组长一个人,他也应该有能力把这个我的项目保护下来。 下面是对组长的要求,这里第1位的是学习能力,就是对于未知领域的酷爱和领悟能力。 接下来说组员。组员第一要务就是把调配下来的工作好好实现。 这外面须要理解力和执行力的造就。这个须要一段时间的磨合,整个团队才可能造成弱小的战斗力。 再一个是主观能动性的造就。如果工作实现了,就应该被动去寻找新的工作去做,有活的时候好好干,没活的时候找活抢着干。 造就主观能动性须要驱动力,一般来说有这么几个: 第一,是自我价值实现的欲望,首先是天生我才必有用的自信,也就是每个人都想做些事件,寻找本身的价值,并把本身价值融入到团队的工作当中。 第二是外在的处分,这些处分能够蕴含物质上的,声誉上的等等。也就是卓越的工作失去了认可。 下面是对于组员的要求,这里处于第1位的是执行力,就是失去指令当前疾速实现工作的能力。 当初说一下工程办法这一块。比拟风行的算是麻利方法论。在麻利方法论中个别有两种方向一种是开发团队驱动,一种是项目经理驱动。不论采纳哪一种方向,这种方法论的一个根本要求就是可能在短期内有看得见的输入,并且有继续的输入。 这种方法论用的难受了的话会给整个团队带来很强的成就感和高昂的斗志,从而激励团队成员把工作当做一种乐趣。在事实的利用中麻利方法论可能会被形式化,比方每天大家都站在那里花几分钟的工夫讲几句话。如果是这样子的话,就走偏了。 为了防止形式化,应该以输入为导向。及时向其余团队成员更新本人的状态。 当初说一下算法和逻辑局部。对于软件技术,我认为大多时候是把它当做一个工程技术来使用的,也就是拿着这个工具去解决理论的用户需要的。在技术使用的过程中,咱们会一直地应用各种各样的算法和逻辑来随机应变的解决咱们的业务流程。对于具体的算法和逻辑,齐全是case by case的。咱们先不深入探讨个例。咱们要探讨一个十分重要的概念,就是复杂度的问题。 我与很多程序员共事过,尤其是高级程序员,发现很多人都有一个习惯,喜爱把简略的问题复杂化。美其名曰要思考周全,要考虑周到。这里说一个很简略的例子,比如说咱们拿到一个我的项目,这个我的项目的需要是援救地球。 很多程序员上来就会陷入到思考如何援救星球的迷雾中。这个思路的第一要务就是要先辨别有多少种星球,而后对这么多的星球进行分门别类。而后在我的项目运行时判断某个输出参数来指定是地球当前,再进入到思考如何援救地球的工作当中去。 如果你问为什么要把这个问题思考的这么简单,因为我的需要只是援救地球而已。一个十分高大上的理由就是他想做一个通用的我的项目,当前能够反对更多的星球,从而不便扩大。 基于这种思路去做我的项目,我的项目会越做越简单,团队会越来越宏大,老本天然也就急剧的回升。 亚马逊在这个方面是吃过很多苦头的。在晚期的我的项目中,有些程序员设计我的项目过于简单,导致这些人升职来到我的项目当前,其他人根本无法接手保护这个我的项目,即便再去找原来的设计者,他们也无能为力了。因为复杂度太高了。 对于流程和工具。这两个方面能够合在一起说。流程须要简洁高效,直击要害解决问题。工具也是一样的。尽管每个人的爱好有些不同,有的人喜爱界面,有的人喜爱命令行,这个都没关系,那就选可能给本人带来最高工作效率的那种工具和流程。 在嵌入式驱动开发畛域外面,有些公司是用一般文本编辑器来写代码的,代码审查是用比拟软件的形式手工合入代码的。尽管驱动式开发中的代码量不是应该特地多,比如说一个driver,如果代码量很大的话,可能就存在设计上的问题了。即便代码量很小的状况下也应该应用比拟先进的工具来解决, 比方代码编辑能够应用vs code, eclipse, qt creator等等,代码审查能够应用平台工具如github, gitlab, bitbucket, gerrit,等,代码查看能够应用git工具( fork, git extensions)等等。 以上只是用一个例子来阐释防止应用十分原始的工具,既容易出错又效率低下。 复杂度当初来谈一谈复杂度的问题,软件开发中的复杂度当然是越低越好。个别谈到复杂度,咱们可能想到了各种逻辑上的复杂度,设计上的复杂度,实际上在软件过程中复杂度波及到方方面面,咱们来看一下,具体有哪些方面咱们须要留神复杂度的问题。 第一是命名规定。先举个例子,我定一个变量叫word。有的人喜爱把它写成wd。这个就减少了这个变量定义的复杂度,你从wd很难明确,这个变量是word的意思。 不论是变量的命名还是函数的命名,咱们都心愿看到名字,咱们应该可能了解这个变量或者函数大体是关联到什么样子的事件。 所以审慎的应用缩写是防止命名规定复杂度进步的重要前提。 第二是程序逻辑的复杂度。线性程序执行的复杂度为1, 呈现分支当前要乘以分支的个数。分支能够是条件判断也能够是循环。所以尽可能的防止分支的呈现是升高程序逻辑复杂度的重要伎俩。 如果程序分支不可避免,要尽可能的把程序分支放到最高的逻辑层。这样做的目标是为了防止在上层解决的时候呈现发散式的分支。发散式的分支会急剧的减少程序的复杂度。 复杂度越高,程序越难保护,复杂度超过肯定水平,人类程序员是无奈解决的。 第三是架构设计的复杂度。架构设计波及到模块设计和零碎设计。要尽可能的把一些专用的模块或者子系统抽取进去,比方平安相干的,日志相干的,工具相干的等等,这些专用的性能可能会被所有其余的业务模块或零碎所调用。 ...

September 4, 2020 · 1 min · jiezi

关于软件工程:我来聊聊前端应用表现层抽象

本文首发于欧雷流。因为我会时不时对文章进行补充、修改和润色,为了保障所看到的是最新版本,请浏览原文。咱们处于变动很快的时代,无论是商业还是科技。一家公司看上去商业很胜利,兴许前脚刚上市,后脚就因为什么而退市,甚至开张;一项看似高大上的技术横空出世,各类媒体争先恐后地撰文介绍,热度炒得老高,没准没多久就呈现了竞争者、替代者。 在这样的大环境下,传统的「web 前端开发」演变成了「泛客户端开发」,前端开发者从「配置工程师」被「逼」成了「软件工程师」。开发变得更简单了,要解决的问题更多了,从业难度不知晋升了多少倍——前端早就不再简略。 在泛滥必须要解决的问题中的一个,就是体现层运行环境的兼容问题,像跨浏览器和跨端、平台、技术栈。留神,这里说的是「体现层」而不是「视图层」。 「体现层」与「视图层」「体现层」的英文是「presentation tier」或「presentation layer」,具体是哪个取决于是物理上还是逻辑上划分;而「视图层」的英文是「view」。「体现层」是「视图层」的超集,依据前端利用的架构设计,它们既能够不等又能够相等。 体现层「体现层」这个词出自经典的三层架构(或多层架构),是其中一个分层。三层架构包含数据层、逻辑层和体现层,个别用在 C/S 架构中。 为什么会在这篇讲前端开发的文章中提到它?这是因为,尽管在一些前端利用中用不到,尤其是快餐式利用,但在企业级简单前端利用中就非常须要一个前端的「三层架构」。 视图层「视图层」则来自体现层罕用的「model-view-whatever」模式中的「view」,即「视图」。至于说的时候在「视图」前面加个「层」字合不适合,就不在这里探讨了,文中皆应用「视图层」这个词。 运行环境兼容跨浏览器因为各浏览器厂商对规范实现的不统一以及浏览器的版本等起因,会导致个性反对不同、界面显示 bug 等问题的呈现。但庆幸的是,他们根本是依照规范来的,所以在开发时源码的语法简直没什么不同。 所谓的「跨浏览器」实际上就是利用浏览器额定的公有个性和技术或辅以 JS 对浏览器的 bug 进行「修改」与性能反对。 跨端、平台、技术栈当初,绝大部分的前端开发者是在做泛客户端开发——开发 web 利用、客户端利用和各类小程序。 在做 web 利用时须要思考 PC 端和挪动端是离开还是适配?技术选型是用 React、Vue?还是用 Web Components?或是用其余的?做客户端利用、各类小程序时这些也会面临技术选型的问题。 如果公司某个业务的性能笼罩了上述所有场景,该如何去撑持?与跨浏览器不同的是,不同端、平台、技术栈的源码语法不一样,要满足业务需要就得各开发一遍。然而,这显然老本过高,并且危险也有些大。 那么,要怎么解决这个问题呢?从源头登程。基本的源头是业务场景,而后是产品设计,但这些都不是开发人员可掌控的,简直无奈扭转。可能齐全被开发人员所左右的根本只有开发阶段的事件,那就从这个阶段的源头动手——源码编写。 若是与业务相干的代码只需编写一次就能运行在不同的端、平台、技术栈上,那真是太棒了!这将会大大地降低成本并缩小危险! 体现层的形象为了达到跨端、平台、技术栈的目标,须要将体现层再划分为形象层、运行层和适配层。其中,形象层是为了对立源码的编写形式,能够是 DSL、配置等,它是一种协定或约定;运行层就是须要被「跨」的端、平台、技术栈;适配层则是将形象层的产物转换为运行层失常运行所须要的模式。 体现层中能够被形象的大略有视图构造、组件外观、组件行为等。 视图构造在 web 前端开发中,HTML 就是一种视图构造的形象,形容了界面中都有什么,以及它们之间的层级关系。最终的显示须要浏览器解析 HTML 后调用操作系统的 GUI 工具库。 对于业务撑持来说,无论是 HTML 还是其余什么拼凑界面的形式,相对来说比拟低级(是「low level」而不是「low」),视图单元的划分粒度比拟细,在开发界面时就会破费更多的工夫。 咱们须要一种可能屏蔽一些不用关注的细节的视图构造形象,在这个形象中,每个视图单元都有着其在业务上的意义,而不是有没有都能够的角色。具体做法请看下文。 组件外观大部分已存在的组件的视觉出现是固定的,即某个组件的尺寸、形态、色彩、字体等无奈被定制。如果同样的交互只是因为视觉上有所差别就要从新写组件,或者在组件内部从新写份款式进行笼罩,那未免也太苦楚了…… 咱们能够将那些心愿可能被定制的视觉出现形象成「主题」的一部分,这部分能够被叫做「皮肤」。在进行定制时,分为线下和线上两种形式。 「线下」是指在利用部署前的开发阶段进行解决。在前端构建工具丰盛的当初,写页面款式时曾经不会去间接写 CSS,而是像 Sass 这种可编程式的预处理器。这样就能够抽取出一些管制视觉出现的 Sass 变量,须要定制时通过在内部对变量赋值进行笼罩,而不须要吃力重写组件或款式。 「线上」则是部署后依据运行时数据动静扭转。在皮肤定制即时预览和低代码平台等场景,是根本没机会去批改 Sass 变量并走一遍构建流程的,即便技术上可能办到。借助 CSS 自定义属性(CSS 变量)的力量能够较为不便地做到视觉出现的运行时变更。 组件行为组件除了外观,其行为也该当是能够定制的。看到「行为」这个词,第一反馈就是跟用户操作相干的事件,然而这里还包含与组件内部结构相干的。 ...

September 2, 2020 · 3 min · jiezi

功能安全26262理论到实践基础概念什么是软件

软件 Sotware 对于什么是软件,似乎所有人都觉得定义是那么的显而易见。直觉上来看,只要砸在我们脚上能疼的,都算是硬件hardware,除此之外的都是软件 Sotware。如果这样的话,使用软件工具设计的专用集成电路( Application-Specific Integrated Circuit ASIC)和基于模型生成的C代码算什么呢? 引用英国铁道安全标准委员会的定义( http://www.yellowbook-rail.org.uk),在2007年的工程安全黄皮书《Engineering Safety Management Yellow Book 3》 中他们认为软硬件的不同在于“软件 Sotware在本质上比硬件更加复杂”“as a rule of thumb,we suggest that if a device has few enough internal stored states that is practical to cover them all in testing, it may be better to regard it as hardware and to show that it meets its safety requirements by analysis of the design and testing of the completed device, including exhaustive testing of all input and state combinations作为一个经验法测,我们建议如果一个系统(device)没有那么多的状态位,而且,这些状态位都可以在实际测试中覆盖的到,我们最好将它看成是一个硬件。我们可以通过分析设计和完全测试(所有输入和状态机组合的穷举测试exhaustive testing)来证明它满足安全需要”。 ...

June 24, 2020 · 1 min · jiezi

我来聊聊面向模板的前端开发

本文首发于欧雷流。由于我会时不时对文章进行补充、修正和润色,为了保证所看到的是最新版本,请阅读原文。在软件开发中,研发效率永远是开发人员不断追求的主题之一。于公司而言,在竞争激烈的互联网行业中,产出得快和慢也许就决定着公司的生死存亡;于个人而言,效率高了就可以少加班,多出时间去提升自己、发展爱好、陪伴家人,工作、生活两不误。 提升效率的途径,无外乎就是「方法」和「工具」。以一个开发者的思维来想,就是将工作内容进行总结、归纳,从一组相似的工作内容中提炼共同点,抽象出解决这一类问题的方法,从而造出便于在今后的工作中更为快速解决这类问题的工具。这个「工具」可以是个函数、组件、中间件、插件,也可以是 IDE、其他开发工具的扩展,甚至是语言。 面向组件在现代前端开发中,如果去问一个业务前端开发:「如何提升团队开发效率?」对方所回答的内容中,极有可能会出现「组件库」。没错,在前端工程化趋近完善的今天,在近几年 React、Vue 等组件化库/框架的影响下,面向组件开发的思维方式早已深入人心。 组件库提效有限现在,组件库已经是一个前端团队的必备设施了,长远来看,团队一定且必须要有自己的组件库。开源的第三方组件库再好,对于一家企业的前端团队来说也只是短期用来充饥的,因为它们无法完全满足一家公司的业务场景,并且出于多终端支持的考虑,必定要进行二次开发或者自研。 组件库有了,团队和公司中推广的效果也不错,绝大多数的人都在用。使用组件开发页面相对 jQuery 时代要每块功能区都得从 <span>、<div> 等 HTML 标签码起来说确实提升了效率,然而有限;要搞出页面需要反复去引入组件,然后组合拼装出来,就像工厂流水线上的工人拼装零件,仍然要去做很多重复动作。 只要觉得当前的开发方式重复的动作多了,就代表还能继续提效,得想个法子减少重复无意义动作。 面向组件的开发方式,是现代前端页面开发提效的初级阶段,也是一个团队所要必经的阶段。 更高层面的提效在之前写的文章中有段话—— 组件可以很简单,也可以很复杂。按照复杂程度从小到大排的话,可以分为几类: 基础组件;复合组件;页面;应用。对,不用揉眼睛,你没有看错! 站在更高的角度去看,「页面」和「应用」也是一种「组件」,只不过它们更为复杂。在这里我想要说的不是它们,而是「基础组件」和「复合组件」。 ——欧雷《我来聊聊面向组件的前端开发》 文中提到了「页面」和「应用」也可以看作是种「组件」。虽然与当时的想法有些差异,但本文的内容就是要在那篇文章的基础上简单聊聊在「页面」层面的提效。 一般来说,「页面」是用户所能看到的最大、最完整的界面,如果能在这个层面有个很好的抽象方案,在做业务开发时与单纯地面向组件开发相比,应该会有更大的提效效果。 GUI 发展了几十年,人机交互的图形元素及布局方式已经相对固定,只要不是出现像 Google Glass 之类的革命性交互设备,就不会发生重大改变。在业务开发中界面形式更是千篇一律,尤其是 web 页面,尤其是中后台系统的 web 页面,一定可以通过什么方式来将这种「千篇一律」进行抽象。 试着来回想下,自己所做过的中后台系统的绝大部分页面是不是我所描述的这样—— 页面整体是上下或左右布局。如果是上下布局的话,上面是页头,下面的左侧可能有带页面导航的侧边栏,或者没有侧边栏直接将页面导航全部集中在页头中,剩余区域是页面主体部分,承载着这个页面的主要数据和功能;如果是左右布局,左侧毋庸置疑就是有页面导航的侧边栏,页头跑到了右侧上面,其余是页面主体。 中后台系统的主要功能就是 CRUD,即业务数据的增删改查,相对应的页面展现及交互形式就是列表页、表单页和详情页。列表页汇总了所有业务数据的简要信息,并提供了数据的增、删、改和更多信息查看的入口;表单页肩负着数据新增和修改的功能;详情页能够看到一条业务数据记录最完整的信息。 每新增一个业务模块,就要又写一遍列表页、表单页和详情页……反复做这种事情有啥意思呢?既然这三种页面会反复出现,那干脆封装几个页面级别的组件好了,有新需求的时候就建几个页面入口文件,里面分别引入相应的页面组件,传入一些 props,完活儿! 这种方式看起来不错,然而存在几个问题: 没有描述出页面内容的结构,已封装好的页面组件对于使用者来说算是个黑盒子,页面内容是什么结构不去看源码不得而知;如果新需求中虽然需要列表页、表单页和详情页,但与已封装好的能够覆盖大部分场景的相关组件所支持的页面有些差异,扩展性是个问题;每来新需求就要新建页面入口文件然后在里面引入页面组件,还是会有很多无意义重复动作和重复代码,时间长了还是觉得烦。我需要一种既能看一眼就理解内容结构和关系,又具备较好扩展性,还能减少重复代码和无意义动作的方式——是的,兜了一个大圈子终于要进入正题了——面向模板开发。 面向模板面向模板的前端开发有三大要素:模板;节点;控件。 富有表达力的模板我所说的「模板」的主要作用是内容结构的描述以及页面的配置,观感上与 XHTML 相近。它主要具备以下几个特征: 字符全部小写,多单词用连接符「-」连接,无子孙的标签直接闭合;包含极少的具备抽象语义的标签的标签集;以特定标签的特定属性的形式支持有限的轻逻辑。为什么不选择用 JSON 或 JSX 来描述和配置页面?因为模板更符合直觉,更易读,并且中立。用模板的话,一眼就能几乎不用思考得看出都有啥,以及层级关系;如果是 JSON 或 JSX,还得在脑中进行转换,增加心智负担,并且拼写起来相对复杂。Vue 上手如此「简单」的原因之一,就是它「符合直觉」的设计。 要使用模板去描述页面的话,就得自定义一套具有抽象语义的标签集。 页面的整体布局可以用如下模板结构去描述: <layout> <header> <title>欧雷流</title> <navs /> </header> <layout> <sidebar> <navs /> </sidebar> <content>...</content> </layout> <footer>...</footer></layout>看起来是不是跟 HTML 标签很像?但它们并不是 HTML 标签,也不会进行渲染,只是用来描述页面的一段文本。 ...

October 8, 2019 · 2 min · jiezi

我来聊聊面向组件的前端开发

本文首发于欧雷流。由于我会时不时对文章进行补充、修正和润色,为了保证所看到的是最新版本,请阅读原文。看到标题,一般会有两种反应: 「哇~好高大上啊!」「嗯,这个话题真大……」 ——的确如此。 深情前戏我不生搬硬套那个什么百科来说啥是「面向组件」和为啥这么做,而是从工作现状以及自己思考的角度来阐述,并试着拟出一个解决方案。 前端眼里的「组件」对于前端开发人员来说,「组件」通常就是指页面上的 UI 组件,主要包括外观和交互。一个合格的组件应该是可复用、可定制、松耦合的,它能够代表一个事物,可以完成一个动作。 组件可以很简单,也可以很复杂。按照复杂程度从小到大排的话,可以分为几类: 基础组件;复合组件;页面;应用。对,不用揉眼睛,你没有看错! 站在更高的角度去看,「页面」和「应用」也是一种「组件」,只不过它们更为复杂。在这里我想要说的不是它们,而是「基础组件」和「复合组件」。 其中,基础组件具有简单的外观和基础的功能,而复合组件则是根据具体场景所进行的基础组件的组合和封装。 为啥要「面向组件」在从事一段时间的前端开发之后,就会发现: 「一个系统里的页面功能怎么都差不多?」「每个网站基本都一个模子里刻出来的!」 ——说得没错! 你在 CTRL + C 并 CTRL + V,改掉相同中的不同之后,保存文件并刷新页面,点这点那看看效果——「我靠!这俩页面的交互一毛一样,怎么在那个页面好好的,到这里就不好使了?!」 1……2……3……个小时过去了,这该死的小强到底是从哪里溜进来的一点儿头绪也没有……心里窝火地一直在「MMP」,一不小心说漏了嘴——「妈卖批的!!!」 兄弟,淡定! 出现这种问题,是因为没有面向组件开发。那些你所觉得的「相似」的部分,就可以提取出来形成组件,以备再次出现类似场景时使用。你以往所依赖的「CTRL + C / V 大法」,讲道理,是下下策中的下下策。 等组件积累得多了,页面就不再是自己苦思冥想一行一行代码挤出来的,而是随手从现成的库中拿来一个一个组件拼出来的。如此一来,不仅页面功能更加稳定,前端开发也能脱离枯燥而变得更加有趣,告别那一整天大部分时间在摁臭虫的鬼日子—— 后端:「什么时候可以联调?」前端:「页面早就弄好了,接口呢?」 后端:「……」 「面向组件」是啥啊换个词,「组件化」,也许更为熟悉。但,所以,到底是指什么呢? 对于抽象概念的含义,每个人都会有自己的理解,正所谓「一千个读者心中有一千个哈姆雷特」。有人会说: 就是把相关的 HTML、CSS、JS 和图片等文件放到同一个文件夹里吧?——没啥毛病。 在进行面向组件开发时,确实会将同一个组件的相关文件放在一个文件夹中,然而,这并不是核心。重要的是,能够将一个复杂的东西恰如其分地拆分成更小且独立的,高内聚低耦合,让别人不必了解其内部运作原理拿来就用——这是思想,也是能力。 进入正题「面向组件」开发,或者说「组件化」,由来已久,并不新鲜。这个话题在前端圈儿也炒了很多年了,这个框架那个库的层出不穷,为什么我现在还要再拿出来嚼一遍呢? 理由很简单: 在别人那不成问题的,在我这可能很是问题;对别人很管用的工具,对我可能并不太适用。别人爽的姿势我不爽要进行面向组件开发,前提是得有可行的技术方案,依我看,需要必备几点: 组件的样式和交互不会意外地被外界干扰——对外隔离;一个组件相关的资源要在我用到时再给我——按需加载;让前端技术不那么强的后端开发也可以用——门槛低。红极一时的充分发挥 jQuery 特长的两个宝儿,jQuery UI 和 Bootstrap 提供了很多 UI 组件,对后端开发人员也很友好,看起来符合要求。但从它们组件的实现方式以及资源加载形式来看—— jQuery UIBootstrap现在的前端圈儿,一提到「组件」,大多数人的兴奋点都在 React、Vue、Angular 等 MV* 框架上。它们是很不错,不仅满足了「对外隔离」和「按需加载」,还大大地提升了前端开发的效率,能大红大紫成这样自有其道理。 我司的业务是 to B 的,因此前端开发场景很「明确」,基本可以简单粗暴地理解为:「前台」就是移动端,「后台」就是桌面端。 前台开发用的是基于 React 和 Ant Design Mobile 二次开发的框架。It works well,能够 hold 住当前的需求。然而,后台开发就不一样了。 ...

October 8, 2019 · 1 min · jiezi

软件开发什么是过度设计

软件设计(架构)往往在项目开发中起到非常关键性的作用,至少它是能够工作。良好的软件设计包含了:灵活性、可伸缩性、可行性、可复用性、安全性,通过该一系列的定义,使我们影响到了软件功能的设计和特征。 (一)、什么是过度设计过度设计一词在英文中称为"over design",over意思是太多,design意思是设计、构思,通过教科书上面的解释,意味着你设计的或构思的太多了,即为过度设计。 什么是过度设计?设计出来的系统比恰到好处要复杂或臃肿的多,过度的封装、继承、接口或是大量的无用配置方法,其实就是用户需要一把杀鸡的刀,而你却设计出了杀牛刀或是电锯。 过度设计通常来自于开发者将问题过于复杂化或是前瞻性欠缺。 在我们日常所犯的错误中,大部分是来自于前者,至于后者的欠缺,需要一定的项目经验和洞察力来支撑,能够合理的预判和考虑需求会哪个方向发展。 在前者,问题复杂化会引入大量额外的代价,如成本上升,系统缺陷增大、提升维护成本、降低系统性能。而高性能和可维护性都是系统的隐性需求,如果这些也没实现好,那就可能属于设计错误。 但是从客观角度来看,能够进行过度设计的,多半设计能力高于设计不足的,过度的设计改回来的成本也比设计不足的改过去的成本低的多,在此需要更多地去权衡"利与弊"。 (二)、过度设计案例以系统充值为例,最初你设计的系统只需要一个支付宝功能,你的数据库设计如下: id primary key int //主键user_id int//充值用户status int //-1充值失败,0充值中,1充值成功order_no string //第三方支付系统订单号amount decimal //金额但是没过多久,你的系统需要接入另一个支付系统-微信,需要区分用户是通过微信还是支付宝充值的,于是你的数据库设计便成了以下模样 id primary key int //主键user_id int//充值用户status int //-1充值失败,0充值中,1充值成功order_no string //第三方支付系统订单号platform string //第三方交易平台amount decimal //金额但是你想了下,感觉可能以后需要接入银联支付,需要记录是哪张银行卡支付的,然后你又想了下,既然已经接入了银联支付,那顺便就再完善以下,支持国际支付,如美元充值,港币充值,然后需要记录上当地充值的汇率及当地支付时间,最终你花了一天的时间,将数据库改成了这样 id primary key int //主键user_id int//充值用户status int //-1充值失败,0充值中,1充值成功order_no string //第三方支付系统订单号platform string //第三方交易平台amount decimal //金额currency string //货币:CNY USD HKD bank_id int //银行卡IDrate decimal // 充值汇率local_pay_time //当地支付时间完成基本设计后,你花了4周的时间完成编码和测试,最终交付了上去,然而系统的初衷只是需要简单区分的是微信充值或支付宝充值,而因过度设计带来的额外成本和缺陷是非常巨大的,为此我们需要尽力让自己做的恰到好处并且避免过度设计。 (三、)如何避免过度设计?避免过度设计的最佳方法就是“不要设计的太远”,未了解实际未来,就做出了各种预设和判断,为系统增加了额外的负担。 正如scrum(敏捷开发)所倡导的Evolutionary Design(演进式设计),将每一次的重构和迭代都映射和更新到最新的设计中来,从而最大限度的满足系统的功能性需求和非功能性需求。 当你手里握着一把锤子时,不要把所有看到的,都当成钉子。

September 8, 2019 · 1 min · jiezi

软件工程思维到底有多重要

最近听音频学习,听到一篇有关软件工程思维的文章,挺想分享给大家,以作讨论。下文转载自 “得到 APP” 万维钢精英日课第三季:《计算机思维 4:工程的复杂》。 这一讲我们要说一个特别厉害的技能,叫做“软件工程”。以我之见,软件工程,可以说是工程管理和综合治理手段的极限。我希望你能从这一讲体会一下如何治理最复杂的系统。 可能你是一个产品经理,主导开发过一款APP。可能你是个企业家,管理一个几万人的大工厂。可能你是个土木工程师,设计过一座跨海大桥。你非常厉害,咱们中国有很多这样的厉害人物。中国是手机 APP 开发大国,中国有很多超大型企业,中国有全世界最长的跨海大桥 ——可是为什么中国就没有属于自己的计算机操作系统呢?为啥国产芯片不行呢? 因为那些事儿,跟现代软件工程相比,还只能算是简单的事儿。 程序员、CEO、计算机科学家,如果是拍一个超级英雄电影的话,这些人都可以是前台的英雄人物。但是躲在幕后操纵世界的,则将是一位、或者几位,软件工程大师。有句话叫“在计算机科学里,软件工程这一部分,对计算机科学家来说太难了。” 不了解软件工程,你就不知道什么叫“大”,什么叫“复杂”。 1.小和大编程是个非常适合自学成才的项目。很多人不是科班出身,自学编程技术,也容易找到一个程序员的职位,甚至还可以自己开发一个小软件。 但仅限于小软件。比如你可以自己写一个电子邮件客户端程序,或者写一个视频编辑工具。可是如果要开发一个超大型软件,其中涉及到的学问,可就不是自学所能达到的了,那是需要在重大项目的实践中去领悟和提高的。自学也许可以让你成为一个优秀的侠客,而伟大的将帅,则只能用千万士兵的鲜血铸就。 这里面的关键是一个尺度问题。大,是不一样的 [1]。 计算机刚刚出来的时候,程序员都是身上有修士气质的手艺人。编程者经常是孤独的,能说天书一样的语言,想法高深莫测,写出来的代码仿佛有一种暴力美学,他们的眼睛跟显示器一起在黑暗中闪闪发光。编程,是一项神秘的技能。 那时候的程序都是完全自由的 —— 计算机很贵,而程序不要钱。程序员们就好像十九世纪的艺术家一样,偶尔弄个俱乐部或者小作坊,彼此欣赏。 不过这个艺术时代并没有持续多长时间,程序员们很快就陷入了极度的悲观情绪之中。因为……错误。 写代码太容易出错了!代码越写越长,出错的频率不成比例地增加。可能你今天费了很大力气好不容易运行通过了,过了几天、遇到一个没想到的情况,发现还有一个隐藏的错误。有个程序员甚至说,他意识到,也许他的余生,都要在纠正自己的错误中度过…… 程序员们终于明白,他们需要工程师思维。 我们之前讲了一些计算机科学的思维,而工程师思维和科学家思维至少有三个重大区别。 第一,科学家是寻找事物的规律,而工程师是去设计一个东西。科学家只要觉得这个规律有意思就可以发表,而工程师得负责任。他得确保这个东西不但要有用,而且还得安全不出事,还得考虑成本,讲究可行性,让人用得上还用得起才行。 第二是对知识的态度。科学家面对知识,是把自己当成一个没有利益攸关的旁观者,感觉看懂了、能总结出规律就行。而工程师,则是参与者。他不能仅仅“懂”这个知识,他是要拿来用的。 第三是对模型的使用。科学家喜欢简化的模型,能抓住实质就行 —— 爱因斯坦有句名言说“什么东西都要越简单越好,要简单到不能再简单为止”。而工程师必须考虑所有的细节,“魔鬼在细节中”是工程师的座右铭。 要把写程序上升到工程的高度,跟以前那种兴趣爱好式的编程可就完全不同了。更进一步,软件工程和传统的工程也不一样。 比如你要修个桥,工程过程中哪里犯个小错误,通常也就是小错误 —— 最多也就是让大桥的质量降级。这座大桥总共有15个桥墩,其中第五个桥墩有个地方没建好,这座桥大致上还能用。但软件就不一样了,程序中的一个小错误很可能就会导致整个系统的崩溃。 这是为啥呢?因为软件不但各处的关联非常密集,而且是个“活”的东西。比如发射火箭,软件是要控制火箭做动作的!哪个动作不对,火箭立即失控。 所以软件不但是个工程,而且比传统工程难得多。那怎么应对这种复杂呢? 2.小思维早期的软件开发者想出了很多工程化的办法,起到了一定的效果。比如以前都是用汇编语言,后来发明了高级编程语言,程序员就不容易出错……当然,这时候也不需要程序员个个都有修士的气质了。 最重要的一个方法,是把常用、好用的代码封装起来,重复使用。如果这段代码总是被用到,已经被大家测试过很多次了,证明没有毛病,那就不要再改来改去搞定制了,我们应该把它封装成一个“库函数”。库函数具有标准化的输入和输出,程序员下次再用的时候只需要照顾好输入输出,而不必关心函数内部是什么情形 —— 这就能大大降低出错的概率和提高编程的效率。 封装这个思想可以用在软件的各个方面。数据结构、面向对象的编程、文件系统,这些都是封装和分层。这一层的编程不用考虑底下一层的逻辑。 操作系统的内核也是一个类似的智慧。操作系统把最常用的操作计算机的动作,都事先在内核中预备好,而内核经过千锤百炼,不容易出错。等到别人写应用软件的时候,用到相关的动作,就只要调用内核就行,而不必自己直接操作计算机。这就相当于把专业的事儿交给专业的人,也就不那么容易出错了。 所有这些思想都要求对软件开发有个宏观的设计,而不只是吭哧吭哧写代码。然后你还得考虑多个人一起开发一个软件的情形,比如最起码得有个版本控制之类。 到这一步,软件业才算正式成了一个行业。在上世纪五十年代,就已经有公司专门开发软件卖钱。 ……可惜这些还远远不够。 软件业从一开始就不是一个做事漂亮的行业。项目总是再延期。好不容易交付了,软件卖出去之后又总是被人发现各种毛病和错误。客户不满意,可是如果真要搞什么售后服务,到现场去给人解决问题,那几乎就是不可完成的任务……而且还有黑客攻击、还有计算机病毒! 我很早以前听过一个笑话,说一个软件工程师嘲笑一个汽车工程师,说“如果汽车行业像计算机行业一样发展,现在汽车应该一毛钱一辆。”但是汽车工程师不以为然,说“可是谁会要一辆动不动就抛锚的汽车呢?” 而早期的软件公司,对此只有两个不是办法的办法。一个办法是尽量去找那些经验丰富、头脑聪明的高水平程序员……一个办法是销售软件的时候干脆附带一个免责声明:如果因为这个软件的毛病给您造成了损失,我们概不负责。 社会对计算机的美好幻想被打破了,软件行业陷入了危机。 3.大思维软件工程的问题不是你每年能培养多少高水平程序员的问题,而是复杂性问题。 小软件和大软件的根本区别在于尺度。以前一个小软件只有几千行代码,现在一个大软件要有几百万行代码。以前的软件是给一个人用,现在是多个用户共同使用一个软件。更重要的一点是,以前的软件是一个人或者几个人开发的,现在则是大型团队一起开发。 计算机思想家弗瑞德里克·布鲁克斯(Fred Brooks),曾经在上世纪六十年代末率领IBM公司300人的团队开发操作系统。他做完这件事之后很有感触,为此专门写了一本书,叫《人月神话》[2]。 布鲁克斯提出两个感慨。 第一个感慨是,1个人干12个月的活,绝对不是12个人在1个月内能干完的。项目用的程序员越多,平均每个人出活的速度就越慢。所以你规划项目的时候不要算什么“人月”。 第二个感慨是,你这个团队做出来的软件的结构,往往和你这个团队的人员组织管理结构高度相似。所以软件工程不但要管项目,还要管人。 布鲁克斯这本书出来,人们才充分认识到软件工程的难度。现代软件工程要求,软件产品必须达到下面这五个目标,称之为“DRUSS” —— Dependable,可信赖,让顾客真能指望上你这个软件;Reliable,得可靠,不能总出毛病;Usable,软件是给人用的,得让人能够上手;Safe,用的时候不能出安全事故;Secure,它得不容易被黑客攻击才行。现代主流操作系统,包括 Windows, Mac 和 Linux,各自都有接近一亿行代码,而且大致实现了这五个方面的要求。而即便是这三个可以说是最成熟的软件系统,其中仍然还有大量的毛病。 那怎么才能获得这种大型软件工程的能力呢?我们前面说的办法都还是小软件思维,剩下的,就只有一些经验之谈,而没有什么特别系统的行动指南了。 比如说,在系统安全方面,软件开发的首要原则是默认不给用户授权。如果非要授权用户接触一个什么东西,就必须得有显性的授权;每个程序进程只能拥有最有限的授权,等等。软件工程就是由这些原则、工作中遇到的规律、前辈传下来的经验组成的。 技术进步能解决一定的问题,比如更多的分层封装,搞虚拟机,客户端和服务器,高级编程语言,交互式开发环境,可视化的控制和数据流,更好的操作系统等等……但是技术解决不了所有的问题。 ...

June 26, 2019 · 1 min · jiezi

有一部分996竟然是这样产生的

大约在10年以前,我跳槽到了一家上市公司。该公司当时在IT行业说不上是大名鼎鼎,但也算有名有号那个水准的。 很快,我很失望的发现,大型上市公司的软件开发团队软件工程和项目管理的水平竟然是这样的: 在立项之初,项目经理就被要求【编制】一份非常详细的项目进度计划提交给客户方和项目管理办公室。详细到什么程度呢?一个周期半年的项目,被要求任务分解至少要有一两千行吧……所以,项目经理处理这样的项目计划的方式就的确是【编制】;我曾经要求项目组的需求分析人员(对于现在的年轻人来讲,可以理解成“产品经理”)在系统分析阶段就需要给出系统原型图(线框图)的设计,没想到居然引起了一番有诸多高手参加的广泛的讨论:系统原型设计应该在分析阶段完成还是在系统设计(现在年轻的开发人员可能不清楚,那个时候系统设计指的是技术和架构层面的设计了)阶段完成?有一个项目团队大约80人,项目经理的项目计划中向公司申请15名专职的测试人员(包括3名测试经理);结果被部门经理给拒绝了(事业部经理亲口讲:让程序员自己测测就行了),最终配给项目组2名实习生作为测试人员;资深的技术经理们写出来的分析文档格式五花八门,各自有各自认为最好的表达方式,就是基本上没有人使用用例分析的方法来表达;大的软件部门中,一共有3个比较大的团队是大领导分别从不同的软件公司挖过来的,因此山头林立……为了让客户觉得合同金额是值得的,因此组建大规模的软件团队常住客户现场(所以必须配备相当比例的初级开发人员);为了让客户觉得合同金额是值得的,因此实行制度化的996;项目的验收和收款不是靠按时保质的提交项目成果,而是靠让用户觉得开发人员实在太辛苦了,实在不忍心不付款了……(这么说真的一点都不夸张)奇怪的是,这样的环境下,自然有人在各种抱怨,但就是没有人试图去发起改变。(当然,后来我知道了,为什么没有人想去改变) 当然,哪个公司都一样,自然有一小部分老员工都成精了。 但是,对于刚刚毕业的毕业生来讲就不一样了,这是一群没怎么见过世面但是可塑性又非常强的人。 想一下,他们刚刚参加工作就进入了这样的环境进行软件开发工作。然后他们中大部分就会自然而然的认为:软件开发这个工种就是这样子的……然后慢慢形成思维习惯……(所以,那些有能力的应届毕业生们,找工作要小心哈。) 当我给大家介绍,软件开发项目可以按时提交、可以不加班、可以保证质量的时候,大家看我的眼神……我基本上可以猜出来他们在想什么:这个大忽悠。 这真的还不是个例,基本上可以称作是普遍现象。(多年之后,老同事们聚会,基本上大家都会感慨:能有当初我们的团队的软件开发管理水准的国内公司,少之又少,不论大小。) 10年过去了,他们中的一部分人可能已经成为老板了吧,然后你就会看到,这些新兴的企业正在实行【非常正常】的996工作制。

April 25, 2019 · 1 min · jiezi

软件工程学习笔记

要想管理好一个软件项目,主要是管理好「人」和「事」,「人」包括项目涉及到到所有关联人员,而管理好「事」就是软件工程要做的事情。 基本理论时间,范围,成本,质量 四个要素不可能面面俱到,如同CAP定理和Base理论一样。一定要让老板和产品经理意识到这个问题,才能顺利进行解决方案到分析和讨论。 风险管理主要风险项目风险:预算、进度、用户、需求等人员风险:离职、人手不足技术风险:引进了项目成员不熟悉的技术、技术不成熟等商业风险:市场反应、产品策略、市场变化和应对策略等应对方法

April 22, 2019 · 1 min · jiezi

[书摘]《敏捷软件开发: 原则、模式与实践》第二部分:敏捷设计(1)

第七章 什么是敏捷设计软件项目的设计是一个抽象的概念。它和程序的概括形状、结构以及每一个模块、类和方法的详细形状和结构有关。可以使用许多不同的媒介去描绘它,但是它最终体现为源代码。最后,源代码就是设计。软件设计的臭味僵化性-设计难以改变脆弱性-设计易遭到破坏牢固性-设计难以重用粘滞性-难以做正确的事情不必要的复杂性-过分的设计不必要的重复-频繁的粘贴,赋值晦涩性-混乱的表达,代码难以理解软件腐化的原因由于需求并没有按照初始设计的方式进行变化,从而导致了软件的退化,改动都很急迫,并且进行改动的开发人员对原始的设计思路并不熟悉,因此,虽然对设计的改动可以工作,但是他却以某种方式违反了原始设计,随着改动的不断进行,这些违反渐渐积累,设计开始出现臭味。敏捷团队敏捷团队依靠变化获取活力,不尽兴预先设计,保持系统设计尽可能的干净,简单,并使用许多单元测试和验收测试作为志愿,保持了设计的灵活性,易于理解性,利用这种灵活性,持续地改进设计,以便于每次迭代结束所生成的系统都具有最适合于那次迭代中需求的设计。敏捷设计敏捷设计是一个过程,不是一个事件。它是一个持续的应用原则、模式以及实践来改进软件的结构和可读性的过程。它致力于保持系统设计在任何时间都尽可能得简单、 干净以及富有表现力。第八章 单一责任原则(SRP)在SRP中,我们把职责定义为变化的原因。如果你能够想到多于一个的动机去改变一个类,那么这个类就具有多于一个的职责。我们需要分离耦合的职责,并对其持久化。结论SRP是所有原则中最简单的之一,也是最难运用的之一。我们会自然地把职责结合在一起。软件设计真正要做的许多内容,就是发现职责并把那些职责相互分离。事实上,我们要将论述的其余原则都会以这样或者那样的方式回到这个问题上。第九章 开放—封闭原则(OCP)软件实体(类、模块、函数)应该是可以扩展的,但是不可修改的。开放封闭原则有两大特征对于扩展是开放的有新的需求或变化时,可以对现有代码进行扩展,以适应新的情况。对于修改是封闭的类一旦设计完成,就可以独立其工作,而不要对类尽任何修改。结论在许多方面,OCP都是面向对象设计的核心所在。遵循这个原则可以带来面向对象技术所声称的巨大好处(也就是,灵活性、可重用性以及可维护性)。然而,并不是说只要使用一种面向对象语言就是遵循了这个原则。 对于应用程序中的每个部分都肆意地进行抽象同样不是一个好主意。正确的做法是,开发人员应该仅仅对程序中呈现出频繁变化的那些部分做出抽象。 拒绝不成熟的抽象和抽象本身一样重要。

March 17, 2019 · 1 min · jiezi

如何优化基于Jupyter的分析/挖掘测试项目

对于一个有软件工程项目基础的程序员而言,我们这群来源「可疑」的Data Scientist最被人诟病的就是期代码质量堪忧到让人崩溃的程度。本篇文章将介绍自己在以python/Jupyter Notebook为基础的分析/挖掘项目时是如何优化代码使其具有更大的可读性(执行效率不是本文的主要目的)。Python语法级别的优化合适的style当然,这个层面的优化是最简单的,大家熟悉的PEP风格和GOOGLE风格都是不错的实践。参加下面两个文档:PEP代码风格GOOGLE代码风格值得一试的命名方案多年经(踩)验(坑)摸索出一套比较适合的变量命名方案,基本的方法是具象词([介词短语])[数据结构]具象词是描述数据的具体用处的词语,例如一个班级的男生的成绩,可以用boy_score来表述。操作则是概括了对数据做过什么处理,如果是个人团队可以维护一个简单的缩略词词库。比如,我们要描述一个班级的成绩做过去空值的处理,可以用drop_null或者rm_na来表示。在这种情况下,我们可以对上面的对象完整描述成boy_score_rm_na。介词短语其实也是操作的一部分,往往以in/over/top(不严谨地归在此类)/group by等。比如,我们这里要描述一个班级的学生按性别取前10的成绩并做了去重处理,可以写成score_unique_groupbysex_top10,如果长度过长,维护一个简写的映射表当然也是不错的(牺牲部分可读性)。数据结构则是描述数据是存储在什么数据结构中的,常见的比如list,pandas.DataFrame、dict等,在上面的例子里,我们储存在pandas.DataFrame则可以写成score_unique_groupbysex_top10_df。而操作和介词短语在很多场合下可以不写。当然在更加抽象地机器学习训练中时,可以以test_df、train_df这种抽象描述是更适合的方案。Jupyter级别的优化线性执行这点是容易忽视的一个问题,任何Jupyter里面的cell一定要保证,具体的cell中的代码是自上而下执行的。这在工作中,可能由于反复调试,导致在编辑cell的过程中不是线性操作。保证notebook可以线性执行的原因,一部分是方便其他阅读人可以正常执行整个notebook;另一部分,也是为了增加可读性。<!– 可接受的例子 –>cell 1import pandas as pd``````cell 2df = pd.read_csv('train.csv')``````cell 3def sum_ab(row): return row['a'] + row['b']``````cell 4df.apply(sum_ab, axis=1)<!– 不可接受的例子,不能正常运行 –>cell 1import pandas as pd``````cell 2df = pd.read_csv('train.csv')``````cell 3df.apply(sum_ab, axis=1)``````cell 4def sum_ab(row): return row['a'] + row['b']载入模块和读入数据放在开头在具体分析中,载入模块和数据是非常常见的工作,而放置在notebook开始容易帮助阅读者注意,需要的依赖以及数据。如果零散地出现在notebook任何地方,这样就容易造成困难的路径依赖检查、模块重命名方式和模块依赖检查。如果有些模块并不常用,但在notebook引用到了,建议在载入模块前的cell中加入一个cell用来安装依赖。jupyter可以用!来实现临时调用系统的命令行,这个可以很好地利用在这个场景中。此外,所有数据和自写模块使用相对链接的方式导入是不错的选择。因为,后期可能别人会通过git的方法获取你的代码,相对链接可以允许我们不修改链接也能使用git项目中的模块和数据。cell 1!pip install scikit-learn``````cell 2import panda as pdfrom sklearn import metricsimport sys## 自编模块sys.path.append('../')from my_module import my_func``````cell 3df = pd.read_csv('./train.csv')一个Cell一个功能我们在具体撰写Jupyter时,无法避免,会反复尝试,并且测试中间输出的结果。因此,很多同行的cell代码往往会呈现以下状态。cell 1df_1 = df.sum(axis = 1)``````cell 2df_2 = df_1.fill_na(0)``````cell 3ggplot(df_2, aes(x = 'x', y = 'y')) + geom_point()这样的做法无可厚非,且并没有错误,但是,这样的缺点是,读者可能需要run三个cells才能得出最终的结果,而中间的处理过程,在阅读报告中,往往是无关紧要的甚至会影响到可读性,具体查看中间步骤只有复现和纠错时才是必要的。因此,我们要保持一个原则,就是一个Cell理应要承担一个功能需求的要求。具体优化如下:cell 1df_1 = df.sum(axis = 1)df_2 = df_1.fill_na(0)## 绘图ggplot(df_2, aes(x = 'x', y = 'y')) + geom_point()但很多朋友可能会遇到,过程过于复杂,导致一个cell看起来非常的冗余,或者处理过程异常漫长,需要一些中间表的情况,后面的建议中,我会提到如何改善这两个问题。数据(包括中间结果)与运算分离回到刚才的问题,很多时候,我们会遇到一个中间过程的运行时间过长,如何改变这种状况呢,比如上个例子,我们发现fillna的时间很长,如果放在一个cell中,读者在自己重新运行时或者自己测试时就会非常耗时。一个具体的解决方案就是,写出临时结果,并且在自己编辑过程中,维持小cell,只在最后呈递时做处理。比如上面的任务,我会如此工作。cell 1df_1 = df.sum(axis = 1)``````cell 2df_2 = df_1.fill_na(0)df_2.to_pickle('../temp/df_2.pickle')``````cell 3ggplot(df_2, aes(x = 'x', y = 'y')) + geom_point()最后呈递notebook时改成如下样子cell 1##~~~~ 中间处理 ~~~~### df_1 = df.sum(axis = 1)# df_2 = df_1.fill_na(0)# df_2.to_pickle('../temp/df_2.pickle')##~~~~ 中间处理 ~~~~##df_2 = pd.read_pickle('../temp/df_2.pickle')## 绘图ggplot(df_2, aes(x = 'x', y = 'y')) + geom_point()这样做的另外个好处可以实现,数据在notebook之间的交互,我们会在之后提到具体场景。抽象以及可复用分离到Notebook外部我们在撰写notebook时遇到的另一个问题,很多具体地清洗或者特征工程时的方法,过于隆长,而这些方法,可能在别的地方也会复用,此时写在一个cell里就非常不好看,例如下面一个方法。cell 1def func1(x): """add 1 """ return x + 1def func2(x): temp = list(map(func1, x)) temp.sorted() return temp[0] + temp[-1]df.a.apply(func2, axis)这种情况的解决方案,是独立于notebook之外维护一个文件夹专门存放notebook中会用到的代码。例如,使用如下结构存放模块,具体使用时再载入。— my_module |__ init.py |__ a.py___ notebook |__ test.ipynb注意使用sys模块添加环境来载入模块。## import cellimport pandas as pdimport syssys.path.append(’../’)from my_module import *但这种方案,存在一个问题——我们会经常改动模块的内容,特别是在测试时,这时候需要能重载模块,这个时候我们需要反复重载模块,python在这方面的原生支持并不友善,甚至重开内核运行所有都比手写这个重载代码快。这时候我们需要一个ipython的magic extension——autoreload,具体的方法参考这个问答。我们只需要在载入模块的开头写上如下行,这样我们每当修改我们自己编写的module时就会重载模块,实现更新。%load_ext autoreload%autoreload 2import pandas as pdimport syssys.path.append(’../’)from my_module import *而模块分离最终的好处是,我们最后可以容易的把这些模块最后移植到生产环境的项目中。项目级别的优化一个notebook解决一个问题为了让项目更加具有可读性,对任务做一个分解是不错的方案,要实现一个notebook只执行一个问题。具体,我在工作中会以下列方案来做一个jupyter的notebook分类。其中0. introduction and contents.ipynb是必须的,里面要介绍该项目中其他notebook的任务,并提供索引。这种方案,就可以提高一个分析/挖掘项目的可读性。- 0. introduction and contents.ipynb- eda.1 EDA问题一.ipynb- eda.2 EDA问题二.ipynb- eda. …- 1.1 方案一+特征工程.ipynb- 1.2 方案一训练和结果.ipynb- 2.1 方案二+特征工程.ipynb- 2.2 方案二训练和结果.ipynb- 3.1 方案三+特征工程.ipynb- 3.2 方案三训练和结果.ipynb- …- final.1 结论.ipynb对文件进行必要的整理一个分析、挖掘的项目,经常包括但不限于数据源、中间文件、临时文件、最终报告等内容,因此一个好的整理项目文件的习惯是必要的。我在工作中,具体采用下面这个例子来维护整个分析/挖掘项目。当然,初始化这些文件夹是一个非常麻烦的,因此,这里分享一个初始化脚本(支持python版本3.6+),大家可以根据自己整理习惯稍作修改。– 项目根目录 |__ SQL:存储需要用的SQL |__ notebook: 存放notebook的地方 |__ 0. introduction and contents.ipynb |__ eda.1 EDA问题一.ipynb |__ eda.2 EDA问题二.ipynb |__ eda. … |__ 1.1 方案一+特征工程.ipynb |__ 1.2 方案一训练和结果.ipynb |__ 2.1 方案二+特征工程.ipynb |__ 2.2 方案二训练和结果.ipynb |__ 3.1 方案三+特征工程.ipynb |__ 3.2 方案三训练和结果.ipynb |__ … |__ final.1 结论.ipynb |__ src: 撰写报告或者文档时需要引用的文件 |__ data: 存放原始数据 |__ csv: csv文件 |__ train.csv |__ … |__ … |__ temp: 存放中间数据 |__ output: 最后报告需要的综合分析结果 |__ *.pptx |__ *.pdf |__ src |__ example.png |__ … |__ temp_module: 自己写的notebook需要引用的模块结语优化一个Jupyter代码并非不可能,只是看是否具有相关的习惯,增加可读性对自己以及团队的工作和开源社区的声望都会有利,希望上面的建议对大家有所帮助。 ...

November 4, 2018 · 2 min · jiezi