为什么shouldComponentUpdate说当前道具是React中的新道具?

时间:2016-04-29 21:32:47

标签: javascript reactjs redux

我正在使用Redux,但不确定这是否是原因。

我有这样的代码

<Page>
  <AnotherChild />
  <Pricing quotes={this.props.item.quotes} />
</Page>

<Pricing>有一个子组件,可以在更改输入时触发调度,从而更新项目的价格。

<Pricing>有这个:

shouldComponentUpdate(nextProps, nextState) {
  console.log(nextProps.quotes[0].value, this.props.quotes[0].value);
}

因此,假设输入为10,我突出显示所有内容并按5,日志显示5以显示下一个和当前道具值。

困惑的是这种情况。我想我需要看一个10的日志 - &gt; 5在某些时候,因为它从10开始并且不能从父母神奇地切换,对吗?

修改

这是一个触发道具更改的代码块。

_updateDiscountAmount() {
  var discountAmount = +this.refs.discount_amount.getValue();

  var quotes = this.props.quotes.map(quote => {

    var promoPrice = quote.value;

    if (Number.isNaN(discountAmount)) {
      discountAmount = 0;
    }

    quote.percentage = discountAmount;

    promoPrice = (promoPrice - (promoPrice * discountAmount/100)).toFixed(2);

    return quote;
  });


  this.props.dispatch({
    type: 'CURRENT_PAGE_UPDATE',
    data: {
      discount_amount: discountAmount,
      quotes
    }
  });
},

2 个答案:

答案 0 :(得分:1)

上面的@wintvelt给出了答案,所以如果他把它写进来,我会标记它。

基本上上面的代码都失败了。即使我正在映射到一个新数组,我正在改变应该是不可改变的。

我需要做的就是解决问题的方法是在修改之前在循环中复制quote

即:

var quotes = this.props.quotes.map(quote => {

  // Copy the object here
  quote = Object.assign({}, quote);

  var promoPrice = quote.value;

  if (Number.isNaN(discountAmount)) {
    discountAmount = 0;
  }

  quote.percentage = discountAmount;

  promoPrice = (promoPrice - (promoPrice * discountAmount/100)).toFixed(2);

  return quote;
});

答案 1 :(得分:1)

当您的nextProps看起来与this.props相同时,通常会在某处无意中改变道具。在一个例子中:

// this.props.quotes = [ { discount : 5 }, { discount : 3}];
var quote = this.props.quotes[0];
console.log(quote.discount);               // 5
quote.discount = 10;                       // (!) this also updates props
console.log(this.props.quotes[0].discount); // 10

要修复,请在更新前制作对象的副本,如下所示:

var newQuotes = this.props.quotes.map(quote => {

  // Copy object
  var newQuote = Object.assign({}, quote);
  ...
  newQuote.percentage = discountAmount;
  ...
  return newQuote;
});