We read every piece of feedback, and take your input very seriously.
To see all available qualifiers, see our documentation.
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Monine's blog
@Monine 同学纯手工打造的 Vue Blog, 和学前班一样也是借用 github issues 做为博客系统
Angular 2.0 Final Release Now Live!
2.0.0 (2016-09-14)
图解7种耦合关系
高内聚与低耦合 内聚是从功能角度来度量模块内的联系,一个好的内聚模块应当恰好做一件事。它描述的是模块内的功能联系。 耦合是软件结构中各模块之间相互连接的一种度量,耦合强弱取决于模块间接口的复杂程度、进入或访问一个模块的点以及通过接口的数据。 要实现的功能。m1和m2是两个独立的模块,其中m2种会显示m1的输入,m1会显示m2的输入。很显然,m1和m2两个模块之间会有一些联系(耦合) 根据耦合程度可以分为7种,耦合度依次变低。 内容耦合: 最紧的耦合程度,一个模块直接访问另一模块的内容 公共耦合: 一组模块都访问同一个全局数据结构 外部耦合: 一组模块都访问同一全局简单变量,而且不通过参数表传递该全局变量的信息。外部耦合和公共耦合很像,区别就是一个是简单变量,一个是复杂数据结构。 控制耦合: 模块之间传递的不是数据信息,而是控制信息例如标志、开关量等,一个模块控制了另一个模块的功能. 从控制耦合开始,模块的数据就放在自己内部了,不同模块之间通过接口互相调用 标记耦合: 调用模块和被调用模块之间传递数据结构而不是简单数据 数据耦合: 调用模块和被调用模块之间只传递简单的数据项参数。相当于高级语言中的值传递 非直接耦合: 两个模块之间没有直接关系,它们之间的联系完全是通过主模块的控制和调用来实现的。耦合度最弱,模块独立性最强。子模块无需知道对方的存在,子模块之间的联系,全部变成子模块和主模块之间的联系。 内聚也分很多种 偶然内聚 逻辑内聚 时间内聚 通信内聚 顺序内聚 功能内聚
高内聚与低耦合
内聚是从功能角度来度量模块内的联系,一个好的内聚模块应当恰好做一件事。它描述的是模块内的功能联系。
耦合是软件结构中各模块之间相互连接的一种度量,耦合强弱取决于模块间接口的复杂程度、进入或访问一个模块的点以及通过接口的数据。
要实现的功能。m1和m2是两个独立的模块,其中m2种会显示m1的输入,m1会显示m2的输入。很显然,m1和m2两个模块之间会有一些联系(耦合)
根据耦合程度可以分为7种,耦合度依次变低。
内聚也分很多种
为什么我不喜欢「前后端分离」
在 v2ex 引起了热烈的讨论 前后端分离大概的意思就是后端只给前端提供数据,前端负责 HTML 渲染(可以在服务器渲染,也可以在浏览器渲染)和用户交互。 为什么做前后端分离? 如果不分离,前端对网站的控制力太弱,没有话语权。 前端想要扩大势力范围。扩大了势力范围才有晋升的机会。 当时前端能控制的,就是 CSS 和 JS 文件。连 HTML 都是放在后端的仓库的。因为 HTML 是由服务器输出的,用到的模板语言就是后端的。 我认同的是「全栈工程师」
在 v2ex 引起了热烈的讨论
前后端分离大概的意思就是后端只给前端提供数据,前端负责 HTML 渲染(可以在服务器渲染,也可以在浏览器渲染)和用户交互。
为什么做前后端分离?
我认同的是「全栈工程师」
Web 开发不应该这么复杂
回顾下从 2004 年开始, Web 开发经历了怎样的过程。 我们对服务器渲染 HTML 的性能不是很满意,同时浏览器的性能进一步提高了,所以我们觉得可以把渲染放到浏览器上来做。 浏览器从服务器得到一个空的页面,然后用 JS 启动这个页面。 JS 发起很多 API 请求。服务器接收 JSON ,输出 JSON 。所有的 HTML 渲染,由浏览器完成。 但是呢,有两个问题: 所以这些 JS 代码和 API 请求,让首页渲染,非常非常非常慢。 所有内容,都无法被搜索引擎检索到。 所以我们决定不用浏览器来渲染首屏了,让服务器来(回到老路子)。但是由于渲染逻辑我们不想做两遍,所以我们需要在服务器添加一个 JS runtime 来执行 JS 才行,这样浏览器端的渲染逻辑在服务器上也能跑起来了。 康威定律说,软件产品的结构就是其创造团队的组织结构的镜像。
回顾下从 2004 年开始, Web 开发经历了怎样的过程。
我们对服务器渲染 HTML 的性能不是很满意,同时浏览器的性能进一步提高了,所以我们觉得可以把渲染放到浏览器上来做。
浏览器从服务器得到一个空的页面,然后用 JS 启动这个页面。 JS 发起很多 API 请求。服务器接收 JSON ,输出 JSON 。所有的 HTML 渲染,由浏览器完成。
但是呢,有两个问题:
所以我们决定不用浏览器来渲染首屏了,让服务器来(回到老路子)。但是由于渲染逻辑我们不想做两遍,所以我们需要在服务器添加一个 JS runtime 来执行 JS 才行,这样浏览器端的渲染逻辑在服务器上也能跑起来了。
康威定律说,软件产品的结构就是其创造团队的组织结构的镜像。
不依赖 Gulp、Babel、WebPack,还能优雅地写代码吗?
前端打包 框架的兴起 MVC 框架(如 Backbone.js) -> MVVM 框架(AngularJS), 此时的库都是不需要额外用 Grunt 做转译的。直到 React 的出现。需要把 JSX 翻译成 JS。此时 Grunt 大概也因为性能太低被 Gulp 取代了。 ECMAScript 的发展 前端开始追新,一定要第一时间用上最新版的 JS 语法。但是即便是 Chrome 和 Firefox 也不可能那么快就支持最新语法。于是前端说,不过就是在 Gulp 里再加一道转译嘛,用 Babel 把 ES 2016 的语法转译成 ES 5 就好了。 DOM 不好用,换成虚拟 DOM CSS 不好用,换成 CSS in JS 浏览器支持的 JS 不好用,换成 ES 最新版语法,然后转译为浏览器支持的 JS DOM Event 不用了,去新造一个 Event 机制。 Gulp 用得太多了 watch 很慢,于是加上了 hot module replacement 实际上这些变化非常适合复杂的 Web 应用,然而 90% 的页面根本不是单页面应用好吗! 能不能让我写一个 CSS 一个 JS 刷新一下就能看到效果!为什么我要花那么多时间来学习转译工具,以及解决转译过程中的各种问题。 总感觉『弊大于利』。甚至有的时候觉得这是『没有问题,创造问题也要上』。
前端打包
框架的兴起
MVC 框架(如 Backbone.js) -> MVVM 框架(AngularJS), 此时的库都是不需要额外用 Grunt 做转译的。直到 React 的出现。需要把 JSX 翻译成 JS。此时 Grunt 大概也因为性能太低被 Gulp 取代了。
ECMAScript 的发展
前端开始追新,一定要第一时间用上最新版的 JS 语法。但是即便是 Chrome 和 Firefox 也不可能那么快就支持最新语法。于是前端说,不过就是在 Gulp 里再加一道转译嘛,用 Babel 把 ES 2016 的语法转译成 ES 5 就好了。
DOM 不好用,换成虚拟 DOM
CSS 不好用,换成 CSS in JS
浏览器支持的 JS 不好用,换成 ES 最新版语法,然后转译为浏览器支持的 JS
DOM Event 不用了,去新造一个 Event 机制。
Gulp 用得太多了 watch 很慢,于是加上了 hot module replacement
实际上这些变化非常适合复杂的 Web 应用,然而 90% 的页面根本不是单页面应用好吗!
能不能让我写一个 CSS 一个 JS 刷新一下就能看到效果!为什么我要花那么多时间来学习转译工具,以及解决转译过程中的各种问题。
总感觉『弊大于利』。甚至有的时候觉得这是『没有问题,创造问题也要上』。
Hybrid APP架构设计思路
Native(以Android为例)和H5通讯,基本原理: Android调用H5:通过webview类的loadUrl方法可以直接执行js代码,类似浏览器地址栏输入一段js一样的效果 webview.loadUrl("javascript: alert('hello world')"); H5调用Android:webview可以拦截H5发起的任意url请求,webview通过约定的规则对拦截到的url进行处理(消费),即可实现H5调用Android var ifm = document.createElement('iframe'); ifm.src = 'jsbridge://namespace.method?[...args]'; JSBridge即我们通常说的桥协议 由于JavaScript语言自身的特殊性(单进程),为了不阻塞主进程并且保证H5调用的有序性,与Native通讯时对于需要获取结果的接口(GET类),采用类似于JSONP的设计理念: 类比HTTP的request和response对象,调用方会将调用的api、参数、以及请求签名(由调用方生成)带上传给被调用方,被调用方处理完之后会吧结果以及请求签名回传调用方,调用方再根据请求签名找到本次请求对应的回调函数并执行,至此完成了一次通讯闭环。 界面与交互(Native与H5职责划分)哪些由Native负责哪些由H5负责? 这个回到原始的问题上来:我们为什么要采用hybrid模式开发?简而言之就是同时利用H5的跨平台、快速迭代能力以及Native的流畅性、系统API调用能力。 总的原则是H5提供内容,Native提供容器 关键界面、安全性要求比较高的界面、交互性强的的界面、UI变更的频率也不高的界面使用Native 导航组件采用Native 导航组件,就是页面的头组件,左上角一般都是一个back键,中间一般都是界面的标题,右边的话有时是一个隐藏的悬浮菜单触发按钮有时则什么也没有。 再者,也是最重要的一点,如果整个界面都是H5的,在H5加载过程中界面将是白屏,在弱网络下用户可能会很疑惑。 所以基于这两点,打开的界面都是Native的导航组件+webview来组成,这样即使H5加载失败或者太慢用户可以选择直接关闭。 系统级UI组件采用Native 默认界面采用Native 设计H5容器 H5离线访问: 顾名思义就是将H5预先放到用户手机,这样访问时就不会再走网络从而做到看起来和Native APP一样的快了。 H5离线动态更新机制: 将H5资源放置到本地离线访问,最大的挑战就是本地资源的动态更新如何设计 Local Url Router 对于H5的请求,线上和离线采用相同的url访问,这就需要H5容器对H5的资源请求进行拦截“映射”到本地,即Local Url Router
Native(以Android为例)和H5通讯,基本原理:
Android调用H5:通过webview类的loadUrl方法可以直接执行js代码,类似浏览器地址栏输入一段js一样的效果
webview.loadUrl("javascript: alert('hello world')");
H5调用Android:webview可以拦截H5发起的任意url请求,webview通过约定的规则对拦截到的url进行处理(消费),即可实现H5调用Android
var ifm = document.createElement('iframe'); ifm.src = 'jsbridge://namespace.method?[...args]';
JSBridge即我们通常说的桥协议
由于JavaScript语言自身的特殊性(单进程),为了不阻塞主进程并且保证H5调用的有序性,与Native通讯时对于需要获取结果的接口(GET类),采用类似于JSONP的设计理念:
类比HTTP的request和response对象,调用方会将调用的api、参数、以及请求签名(由调用方生成)带上传给被调用方,被调用方处理完之后会吧结果以及请求签名回传调用方,调用方再根据请求签名找到本次请求对应的回调函数并执行,至此完成了一次通讯闭环。
界面与交互(Native与H5职责划分)哪些由Native负责哪些由H5负责?
这个回到原始的问题上来:我们为什么要采用hybrid模式开发?简而言之就是同时利用H5的跨平台、快速迭代能力以及Native的流畅性、系统API调用能力。
总的原则是H5提供内容,Native提供容器
关键界面、安全性要求比较高的界面、交互性强的的界面、UI变更的频率也不高的界面使用Native
导航组件采用Native
导航组件,就是页面的头组件,左上角一般都是一个back键,中间一般都是界面的标题,右边的话有时是一个隐藏的悬浮菜单触发按钮有时则什么也没有。
再者,也是最重要的一点,如果整个界面都是H5的,在H5加载过程中界面将是白屏,在弱网络下用户可能会很疑惑。
所以基于这两点,打开的界面都是Native的导航组件+webview来组成,这样即使H5加载失败或者太慢用户可以选择直接关闭。
系统级UI组件采用Native
默认界面采用Native
设计H5容器
H5离线访问: 顾名思义就是将H5预先放到用户手机,这样访问时就不会再走网络从而做到看起来和Native APP一样的快了。
H5离线动态更新机制: 将H5资源放置到本地离线访问,最大的挑战就是本地资源的动态更新如何设计
Local Url Router
对于H5的请求,线上和离线采用相同的url访问,这就需要H5容器对H5的资源请求进行拦截“映射”到本地,即Local Url Router
哪个蠢蛋写的烂代码?
你既可能是那个吐槽别人给你留下了麻烦,也可能是别人嘴里那个制造麻烦的人。 最难的不是自己写代码,而是维护别人写的代码,在复杂的逻辑中找到某一个隐藏得很深的bug,或者在某个(些)位置添加一些代码以实现新的功能。你需要按照最初实现者的思路去理解,这往往是最难的,这个过程中非常让人容易产生挫败感和不良情绪。 设计太复杂 性能不好 各种无法理解的逻辑 其实有时候我们不理解的,不是人家用的差,而是我们的格调低。我开始收起我的傲慢,不会一上来就指责别人,对不甚了解的领域保持敬畏,以免看起来像个小丑。 好的代码是什么样子的呢? Bjarne Stroustrup(C++之父)说: 逻辑应该是清晰的,bug难以隐藏。 依赖最少,易于维护。 错误处理完全根据一个明确的策略。 性能接近最佳,避免代码混乱和无原则的优化。 整洁的代码只做一件事。 Michael Feathers(《修改代码的艺术》作者)说: 整洁的代码看起来总是像很在乎代码质量的人写的。 没有明显的需要改善的地方。 代码的作者似乎考虑到了所有的事情。 可以感受到,对好的代码的理解有很多共通的地方: 代码简单,代码意图明确,其他人才容易与你协作。 可读性和可维护性要高。 以最合适的方式解决问题。 程序员有三种 拿钱干活,不爽就换 - 程序员只是一份工作。 只要能实现功能就好,学习进步太累了。 热爱程序本身的人, 这些人可能只有1%, 他们有目标的写程序, 他们愿意思考, 愿意听取正确地/更好的方法, 他们会热爱学习新的东西。优秀的工程师在思考、重构 明年的今天「其他」工程师还写一样的代码, 唯一不一样的是Ta老了一岁。 进阶的经验 多看书,多读其他人的博客,阅读优秀的开源项目的代码甚至语言本身的源代码. 看代码要思考别人为什么这样写 想好了再开始写 给自己提要求。实现过程中不断的提高要求,这个要求就是比你现有的能力要高一点点 选择更强的队友。遇见什么样的人,就会变成什么样子的人 对别人吐槽狠 可能有一天, 看到一段代码,骂了句「哪个蠢蛋写的烂代码?」 结果git blame一看原来是自己写的。恭喜你,你进阶了!
你既可能是那个吐槽别人给你留下了麻烦,也可能是别人嘴里那个制造麻烦的人。
最难的不是自己写代码,而是维护别人写的代码,在复杂的逻辑中找到某一个隐藏得很深的bug,或者在某个(些)位置添加一些代码以实现新的功能。你需要按照最初实现者的思路去理解,这往往是最难的,这个过程中非常让人容易产生挫败感和不良情绪。
其实有时候我们不理解的,不是人家用的差,而是我们的格调低。我开始收起我的傲慢,不会一上来就指责别人,对不甚了解的领域保持敬畏,以免看起来像个小丑。
好的代码是什么样子的呢?
Bjarne Stroustrup(C++之父)说:
Michael Feathers(《修改代码的艺术》作者)说:
可以感受到,对好的代码的理解有很多共通的地方:
程序员有三种
明年的今天「其他」工程师还写一样的代码, 唯一不一样的是Ta老了一岁。
进阶的经验
可能有一天, 看到一段代码,骂了句「哪个蠢蛋写的烂代码?」 结果git blame一看原来是自己写的。恭喜你,你进阶了!
一家初创公司的 CTO 应当做什么
像是技术问题,但是当你深入分析问题的本质时,你会发现它们实际上是人的问题 主要工作是确保公司的技术策略服务于它的商业策略 将它分解为五个特定的技能 平台选择与技术方案设计 把控全局(包括一些关键细节) CTO 是整个项目中能够了解整套技术方案能做什么不能做什么的人。这意味着了解什么可行,什么不可行,当前架构能支持什么,做不到什么,以及构建一个新功能在先有架构下要多长时间 提供选择 从不说 “这是不可能的” 或 “我们永远别这样做”。相反找到可选方案并且能够就这些方案与其他人沟通 80/20原则 找到一个获得 80% 好处而只要消耗 20% 成本的折衷方案 培养技术 leader
像是技术问题,但是当你深入分析问题的本质时,你会发现它们实际上是人的问题
主要工作是确保公司的技术策略服务于它的商业策略
将它分解为五个特定的技能
平台选择与技术方案设计
把控全局(包括一些关键细节)
CTO 是整个项目中能够了解整套技术方案能做什么不能做什么的人。这意味着了解什么可行,什么不可行,当前架构能支持什么,做不到什么,以及构建一个新功能在先有架构下要多长时间
提供选择
从不说 “这是不可能的” 或 “我们永远别这样做”。相反找到可选方案并且能够就这些方案与其他人沟通
80/20原则
找到一个获得 80% 好处而只要消耗 20% 成本的折衷方案
培养技术 leader
尺寸规范
班会第 10 期分享过一张尺寸的图, 这里的内容更方便查看
UI设计师导航网
UI设计师常用网站收集
The text was updated successfully, but these errors were encountered:
No branches or pull requests
Monine's blog
Angular 2.0 Final Release Now Live!
图解7种耦合关系
为什么我不喜欢「前后端分离」
Web 开发不应该这么复杂
不依赖 Gulp、Babel、WebPack,还能优雅地写代码吗?
Hybrid APP架构设计思路
哪个蠢蛋写的烂代码?
一家初创公司的 CTO 应当做什么
尺寸规范
UI设计师导航网
The text was updated successfully, but these errors were encountered: