当前位置: 首页 > 面试题库 >

如何从jQuery转到React.js?

南宫勇军
2023-03-14
问题内容

我已经读了几天的React。我可以理解大部分的内容,但是我对自己的编写能力并不完全自信。我一直在研究一个小型Web应用程序,该应用程序通过jQuery完成所有html生成并将元素彼此附加。我想尝试用React重建它,因为我相信它会更快。这个JSFiddle是我正在从事的工作的一个小例子。您将如何使用React编写它?

JS:

function remove() {
    this.remove();
}

function timed_append_new_element() {
    setTimeout(function () {
        var added_content = $("<span />", {
            class: "added_content",
            text: "Click to close",
            click: remove
        });
        container.append(added_content);
    }, 3000);
}

function append_new_element() {
    var added_content = $("<span />", {
        class: "timed_added_content",
        text: "Click to close",
        click: remove
    });
    container.append(added_content);
}


var container = $("<div />", {
    class: "container"
});
var header = $("<span />", {
    class: "header",
    text: "jQuery to React.js Header"
});
var add_button = $("<button />", {
    class: "add_button",
    text: "Add Element",
    click: append_new_element
});
var timed_add_button = $("<button />", {
    class: "add_button",
    text: "Add Element in 3 seconds",
    click: timed_append_new_element
});
container.append(header);
container.append(add_button);
container.append(timed_add_button);
$("body").append(container);

问题答案:

需要牢记一些基本原则,这些原则可以帮助您构建良好的React应用程序:

您的UI应该是数据的函数

在许多“jQuery汤”式的应用程序中,应用程序的业务逻辑,应用程序的数据和UI交互代码都是混杂在一起的。这使得这类应用程序难以调试,尤其是难以增长。像许多现代的客户端应用程序框架一样,React强制实现了UI只是数据表示的想法。如果要更改UI,则应更改一条数据,并允许框架使用任何绑定系统为您更新UI。

在React中,每个组件(理想情况下)是两个数据的函数- 传递给组件实例属性 ,以及组件内部管理的 状态
。给定相同的属性(或“属性”)和状态,组件应以相同的方式呈现。

如果没有具体示例,这可能是一个抽象的想法,因此在继续进行操作时请牢记这一点。

不要碰DOM

在React中,甚至比其他数据绑定框架更重要的是,您应该尽可能不要直接操纵DOM。由于React使用内部带有差异算法的虚拟DOM来对实际DOM进行操作,因此许多React的性能和复杂性特性都是可能的。每当您构建一个伸出手并执行自己的DOM操作的组件时,您都应该问自己是否可以使用React的虚拟DOM功能更惯用地构建相同的功能。

当然,有时您需要访问DOM,或者想要合并一些jQuery插件而不在React中重建它。在这种情况下,React为您提供了良好的组件生命周期挂钩,您可以使用它们来确保React的性能不会受到太大的影响(或者在某些情况下,可以防止组件遭到破坏)。

不操纵DOM与上面的“ UI作为数据的函数”紧密相关。

反转数据流

在大型React应用程序中,可能很难跟踪哪个子组件正在管理某些应用程序数据。因此,React团队建议将数据操作逻辑保持在中央位置。最简单的方法是将回调传递到子组件中。Facebook还开发了一种名为Flux的架构,该架构拥有自己的网站。

创建可组合的组件

很多时候,编写一个大型组件来管理多个状态或多个UI逻辑可能很诱人。在可能的情况下(并且在合理的范围内),您应该考虑将较大的组件分解为较小的组件,这些组件可以对单个数据或UI逻辑进行操作。这使得扩展和在应用程序的各个部分之间移动变得容易得多。

当心可变数据

由于仅应通过this.setState从组件内部调用来更新组件状态,因此请警惕易变数据。当多个函数(或组件!)可能在同一时刻更新可变对象时,这是双重事实。React可能会尝试批处理状态更改,并且您可能会丢失更新!如Eliseu
Monar的评论中所述,请考虑在对可变对象进行突变之前对其进行克隆。React具有可以提供帮助的不变性助手。

另一个选择是完全放弃直接保持可变数据结构的状态。上面提到的“助焊剂”模式对这个想法很有趣。

在React站点上有一篇很棒的文章,名为《ReactinginReact》,它探讨了如何将一个想法或一个模型转化为一个React应用程序,我强烈建议您仔细研究一下。作为一个具体示例,让我们看一下您提供的代码。实际上,您需要管理一个数据:container元素内部存在的内容列表。用户界面的所有更改都可以通过对该数据的添加,删除和更改来表示。

通过应用上述原则,您的最终应用程序可能看起来像这样:

/** @jsx React.DOM */

var Application = React.createClass({
  getInitialState: function() {
    return {
      content: []
    };
  },

  render: function() {
    return (
      <div className="container">
        <span className="header">jQuery to React.js Header</span>
        <button className="add_button"
                onClick={this.addContent}>Add Element</button>
        <button className="add_button"
                onClick={this.timedAddContent}>Add Element in 3 Seconds</button>
        {this.state.content.map(function(content) {
          return <ContentItem content={content} removeItem={this.removeItem} />;
        }.bind(this))}
      </div>
    );
  },

  addContent: function() {
    var newItem = {className: "added_content", text: "Click to close"},
        content = this.state.content,
        newContent = React.addons.update(content, {$push: [newItem]});
    this.setState({content: newContent});
  },

  timedAddContent: function() {
    setTimeout(function() {
      var newItem = {className: "timed_added_content", text: "Click to close"},
          content = this.state.content,
          newContent = React.addons.update(content, {$push: [newItem]});
      this.setState({content: newContent});
    }.bind(this), 3000);
  },

  removeItem: function(item) {
    var content = this.state.content,
        index = content.indexOf(item);
    if (index > -1) {
      var newContent = React.addons.update(content, {$splice: [[index, 1]]});
      this.setState({content: newContent});
    }
  }
});

var ContentItem = React.createClass({
  propTypes: {
    content: React.PropTypes.object.isRequired,
    removeItem: React.PropTypes.func.isRequired
  },

  render: function() {
    return <span className={this.props.content.className}
                 onClick={this.onRemove}>{this.props.content.text}</span>;
  },

  onRemove: function() {
    this.props.removeItem(this.props.content);
  }
});

React.renderComponent(<Application />, document.body);
您可以在 此JSFiddle中查看运行中的代码: http
//jsfiddle.net/BinaryMuse/D59yP/

该应用程序由两个组件组成:一个名为的顶级组件Application,它管理(处于其状态)一个数组content,一个名为的组件ContentItem,该组件代表该数组中单个项目的用户界面和行为。Applicationrender方法ContentItem为content数组中的每个项目返回一个元素。

需要注意的一件事是,用于管理content数组内部值的所有逻辑都是在Application组件中处理的。该ContentItem成分被送到一个
_参考_到ApplicationremoveItem方法,其中所述ContentItem点击时委托给。这将所有用于操作状态的逻辑保留在顶级组件内。



 类似资料:
  • viewServlet.java: 我的目标是将'viewservlet.java'中的html代码编写为'result.jsp'中的纯html代码。 我所期望的是,如果我用jsp编写纯html代码,那么所有的记录都将从“MySQL”中检索,将显示在viewservlet.java中。如果我想要编辑,那么删除将发生在“viewservlet.java”中 我尝试了Request.GetAttrib

  • 我如何将此代码从juqery转换为vuejs? 此处的Javascript测试:https://codepen.io/tidiosupport/pen/wnepeao

  • 问题内容: 我已经编写了这个jQuery ajax方法,在下面调用了webmethod。除了作为用户对象的参数具有空字段之外,调用进行得很好。我在调试时可以在firebug中看到值,但它们无法通过webmethod中的User对象参数 我试图从jQuery方法传递给Webmethod的两个值是“ UserID”(Guid)和“ About”(字符串),它们都是User类的属性,但在服务端,是Use

  • 我已经集成了从贝宝到贝宝帐户的钱转移在我的应用程序,但现在我想转移金额从我的贝宝帐户到任何信用卡。有没有人可以帮助我在这方面发送代码或链接,在那里实现?先谢谢你。

  • 问题内容: 我正在尝试从从mysql数据库获取数据的php文件对div进行简单的ajax更新。一个函数填充div,另一个函数将消息添加到数据库,并在单击提交按钮时调用。我想知道是否有人可以在jQuery中给我他们的同等学历。以下是原型版本。 问题答案: 在jQuery的阿贾克斯()调用,所有这一切。它具有较少参数的包装器,例如.get()、. post()和.load(),您可以使用这些包装器来减

  • 问题内容: 我有一个选择标签,如下所示: 并且我为此使用了jQueryUI控件(组合框),则从jQuery触发的事件“更改”不会触发doSomething()。 您知道如何从外部角度触发ng-change吗? 问题答案: 糟糕-这是很糟糕的做法-但您可以使用目标控制器中驻留的元素并从中获取。 例: Javascript: 现在,您的变量可以访问控制器上定义的所有方法。