[翻译]React抛开事物看本质

news/2024/7/3 2:29:06

React JSX: The Other Side of the Coin

React发布的时候,很多人看到JSX都迷失方向(lost their minds)。javascript中的那些括号是干什么的?! 那么关注点分离理念呢? Facebook没有从社区中引荐什么吗?

至少可以这样说,和很多人一样,我对JSX最初的反应也是持怀疑态度的(skeptical)。但是当我渐渐喜欢上React的时候,每当我介绍给新开发者,我就感觉在秀自己的丑宝宝(作者真幽默,还秀上了自
己爱子照片,这里省略掉)。

尽管有最初的想法,但后来我意识到JSX根本不是激进的(radical)想法。实际上,这就是事情的另一面。这是自然的演化转换过程。(It’s a natural evolutionary transition.) 为了理解为什么是这
样,请看后续故事。

阶段1: 非侵入式Javascript(Unobtrusive JavaScript)

非侵入式Javascript就是说HTML标签中不嵌入任何javascript代码。还记得jquery时代的那些日子吗? 非侵入式Javascript时代可谓百花齐放(in full bloom)。HTML是纯HTML, Javascript也是纯Javascript。关注点是完全分离的。

HTML代码可以这样写:

<a class=”hide”>Click to hide me</a>

Javascript代码可以这样写:

$('.hide').click(function() {-
  $(this).hide();
}-

完胜了,是不是? 其实不然。

似乎这是非常棒的思想。 HTML完全纯正!但是随后我们会发现一些问题: 我们怎么告知两者的互联关系呢? 答案是: 除非看完Javascript的每行代码,否则不能确定两者关系是啥。 这种模式中,要修>改HTML标签中的某行,就必须检查javascript中的每一行来确保这样修改没有破坏选择器。你瞧,这里实际上并没有做到完全的分离。确实,JS和HTML是在独立文件中了,但是这两个技术基本上是完全
联系在一起的(骨肉相连??join at the hip)。两者必须步调一致(lockstep),否则应用将会奔溃。

严格的HTML和JS的分离,实际上导致应用难于维护调试。每当修改标签行的时候,必须考虑是否破坏某个jQuery选择器。也许放宽对关注分离的信仰,我们也许会可能会减轻一些痛苦吧。(Perhaps if we relaxed our religious devotion to separation of concerns, we could relieve some of this pain?)这就迎来了第二个阶段的故事…

阶段2: 双向绑定

当前端开发看到Knockout和Angular的双向绑定的时候,这是一个启发。我们就在关注点分离与HTML中包含强大声明绑定之间摇摆。(Many of us tossed our religious devotion to separation of concerns and embraced the power of declaring bindings in HTML.)当数据改变的时候,UI就更新。当UI改变的时候,数据也随之改变。如此干净,如此简单。

的确,每个类库和框架都有自己的一套实现方式,但是基本上做的都是同样的事情。简单看看几个流行框架中对数组迭代的简单例子:

//Angular
<div ng-repeat="user in users">

//Ember
{{#each user in users}}

//Knockout
data-bind="foreach: users"

这里好戏上演了。 几乎没有人意识到一个非常基本的问题: 这里我们实际上在HTML中放入了Javascript。这就不符合关注点分离的理念。上面所有的方法都做同样的一件事情: 通过添加额外专门的标>签,让HTML更加强大。这些标签实际上被解析为Javascript。我们最终非常舒服的将JS和HTML以此方式混合, 是时候介绍React,以及事情的另一面......

阶段3: JSX

React的JSX不是激进演变。它只是简单的认知成果: 作为一个行业,我们已经确定(有共识):-

HTML和Javascript是胞兄胞弟。

诚然,我们只是没有大声说出来而已。但是对Angular, Knockout和Ember的拥抱,让我们新的偏好更明确。上面已经确定,在HTML中写入数据绑定是一种有效的将JS注入HTML的方式。但是我们要混合,
为什么选择加强一个像HTML一样软弱涣散的技术呢。浏览器从出现的时候就松散的解析HTML。那么HTML是声明数据绑定,循环以及条件逻辑的逻辑基础吗?

Facebook认为Javascript是更加合适的处理这两种混合关系的逻辑和强大技术。 真谛在于(Facebook recognized that JavaScript was a more logical and powerful technology for handling these two intermingled concerns. The epiphany comes down to this):

Angular, Ember和Knockout是在HTML中放置JS。
而React是将HTML放置在JS中。

此举优势有多处,你还没有尝试React和JSX的话可能不会完全意识到。React的JSX在下面几个原因下比阶段2中所有类型的框架更优胜:

1. 编译时错误(Compile-time Errors)

如果你在HTML中打错字,一般来说你不知道哪里出了问题。很多情况下都是客户端运行时错误。例如,在使用angular的时候,如果将ng-repeat错误打成n-repeat,不会发生任何事情。同样对于Knockout来说如果将data-bind错误输入为data-bnd也是一样的。这两种情况,应用都会在运行时悄无声息的失败。那是相当沮丧的(frustrating)。

与此相比,在JSX中如果打印错误,根本不会编译。忘记闭合<li>标签? 你是否乐意在你HTML中打印错误的时候获得丰富的反馈呢?

ReactifyError: /components/header.js: Parse Error: Line 23: Expected corresponding JSX closing tag for li while parsing file: /components/header.js

使用JSX, 这种详细的反馈最终成为现实!很难过分强调(overemphasize)这点上面到底优胜多少。这种快速反馈循环极大提高了生产力。正如在我的整洁代码课程中讨论的,精心设计的解决方案失败快
速(well-engineered solutions fail fast)。

2. 完全利用Javascript的强大功能(Leverage the Full Power of JavaScript)

在Javascript中组成标签,意味着在使用标签的时候可以尽情享受所有Javascript的强大能力,而不是那些HTML为中心的框架,例如Angular和Knockout, 所提供的少量特殊子集所提供的能力。

客户端框架不应该需要用户学习声明循环和条件语句的专属语法。

React避免学习另外一种专属声明循环和条件语句方式的开销。正如你在阶段2中所见到的,每个双向绑定框架都利用自己特殊语法来实现这些。相比而言,JSX看起来几乎和HTML等价,它使用简单的面>相对象Javascript(ol Javascript)来实现诸如条件和循环的。在各自为政的Javascript生态系统中,不需要学历另外一种专属的数据绑定语法显然略胜一筹。(In an ecosystem as fragmented as JavaScript, not having to learn yet another proprietary data binding syntax is a nice win.)

既然标签和相关联的javascript在同一个文件中书写, 很多IDE也会在你引用函数的时候提供一些智能支持。想象一下在面相HTML的框架中,引用函数的时候会有多么频繁的输入错误。

结语(Final Thoughts)

JSX不是激进的思想。它是自然进化过程的产物。因此尽量不要抓狂。

JSX不是革命,而是进化。
JSX isn’t revolutionary. It’s evolutionary.

正如多数的进化形式,它是一种明智的改进。

是否想要了解更多? 那么请进入我的新课程, 基于pluralsight.com网站上面的(多元视角)"使用React和Flux构建应用程序"

Check out my new course “Building Applications with React and Flux” on Pluralsight.

翻译原文地址:

  • React: The other side of the coin

  • www.mh611.com/blog

  • joescott.coding.me/blog


http://www.niftyadmin.cn/n/4153408.html

相关文章

客户端开发 Windows驱动开发(1)SDK WDK DDK WDM的关系

尽管Windows平台的SDK、DDK与WDK都包含了WinDBG工具包&#xff0c;但是用户获取WinDBG工具包的最主要方式还是从微软网站自由下载&#xff0c;因为这样获得的版本最新。 最近因为工作需要&#xff0c;尝试去了解WINDOWS下的驱动开发&#xff0c;现在总结一下最近看到的资料。 …

客户端开发 Windows驱动开发(2)搭建QT开发环境--注意MSVC和MingW的区别

Qt 中有两种方式编译&#xff1a;一种是MinGW &#xff0c;另一种MSVC&#xff0c;是两种不同的编译器。 1、MSVC是指微软的VC编译器 2、MingGW是指是Minimalist GNU on Windows的缩写。它是一个可自由使用和自由发布的Windows特定头文件和使用GNU工具集导入库的集合&#xf…

客户端开发 Windows驱动开发(3)注意调试工具gdb和windbg常用调试命令

由于工作的需要&#xff0c;本人常常需要在gdb和windbg调试器上来回切换&#xff0c; 经常会弄混淆这两者的命令&#xff0c;现做个对照表&#xff0c;方便随时查阅。本人也经常用到ollydbg&#xff0c;但由于od界面很友好&#xff0c;不太需要用到命令&#xff0c;况且od的命令…

Advanced Auto Layout:Changing Constraints

Changing Constraints改变约束 A constraint change is anything that alters the underlying mathematical expression of a constraint (see Figure 17-1). You can learn more about constraint equations in Anatomy of a Constraint. 一个约束的改变是什么&#xff0c;改变…

VMware deepin 20 安装 解决网络问题

详细的安装过程见后面&#xff0c;为了方便自己查阅&#xff0c;我先记录一下&#xff0c;安装后不能连通网络的问题&#xff1a; 1、我选用桥接模式&#xff0c;之前虚拟机网络适配器种我没有配置桥接模式。&#xff08;打开虚拟网络编辑器&#xff0c;添加网络&#xff0c;然…

Linux shell 脚本监控cpu,内存,硬盘,网络,是否存活

写脚本的背景&#xff1a;脚本实现简单的监控&#xff0c;而不需要用非常的重的监控软件完成。脚本如下#!/bin/sh # 脚本放入到/usr/local/bin # chmod 755 check_server.sh # crontab 中添加 source /etc/bashrc#------监控阈值 DISK_space_warn90 CPU_load_warn5 CPU_use_war…

C++ ——Qt的信号和槽的详解

1、概述 信号槽是 Qt 框架引以为豪的机制之一。所谓信号槽&#xff0c;实际就是观察者模式。当某个事件发生之后&#xff0c;比如&#xff0c;按钮检测到自己被点击了一下&#xff0c;它就会发出一个信号&#xff08;signal&#xff09;。这种发出是没有目的的&#xff0c;类似…

nginx负载均衡+keepalive心跳检测

环境标准&#xff1a;一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一一内核&#xff1a;2.6.32-642.el6.x86_64系统&#xff1a;CentOS release 6.8 (Final)ip&#xff1a;web01:10.0.0.8 …