【问题标题】:Why can't I set a dynamic property inside a nested function?为什么我不能在嵌套函数中设置动态属性?
【发布时间】:2020-06-13 13:00:30
【问题描述】:

我正在尝试创建一个可以像这样动态设置对象属性的函数:

void main() {
  final obj = Item();

  obj.update(5);

  print(obj.xVal);
}

class ObjectBase {
  void _setData(current, newValue) {
    current = newValue;
    print(current);
  }
}

class Item extends ObjectBase {
  int _x;

  int get xVal => _x;

  update(x) {
    _setData(_x, x);
  }
}

_setData 中的 print 语句工作正常,但它实际上并没有改变 _x,即使它已经通过了。我希望在此处更改引用会在任何地方更新它。

那么为什么这不起作用,有解决办法吗?

您可以假设我确实有充分的理由在update 中调用_setData,而不仅仅是在update 中实现功能。

更新:

我正在努力实现的真实生活示例

class ViewModel extends ChangeNotifier {
  void _setDataFromDependency(current, newValue) {
    if (!deepDynamicEquality(current, newValue)) {
      current = newValue;
      notifyListeners();
    }
  }
}

class ListScreenViewModel extends ViewModel {
  int _localCount = 0;
  List<int> _globalList;

  ListScreenViewModel();

  List<int> get globalList => _globalList;
  int get localCount => _localCount;

  incrementLocal() {
    _localCount++;
    notifyListeners();
  }

  void update(ListStore listStore) {
    _setDataFromDependency(_globalList, listStore.globalList);
    // if (!deepDynamicEquality(_globalList, listStore.globalList)) {
    //   _globalList = listStore.globalList;
    //   notifyListeners();
    // }
  }
}

【问题讨论】:

  • 不这么认为。无论值是原始值还是对象,我的代码都不起作用
  • 看看_setData(_x, x);。您期望 _x 在作为参数给出时可以更新,这是不可能的。这就是我链接到另一个问题的原因,因为您希望通过引用传递。
  • 所以不能在函数中传递引用?
  • 在 Dart 中不可能。如果您将对象的引用作为参数发送,则引用(指针)将被复制,但您仍然可以更改引用指向的对象的状态(例如,如果您发送对列表的引用,则可以添加元素到列表,但您不能将引用更改为指向另一个列表对象)。

标签: flutter dart


【解决方案1】:

一个过于简单的解决方法是 return 来自 _setData 的值。 @julemand101 已经回答了限制。

class ObjectBase {
  int _setData(current, newValue) {
    current = newValue;
    print('current: $current');
    return current;
  }
}

class Item extends ObjectBase {
  int _x;

  int get xVal => _x;

  update(x) {
    _x = _setData(_x, x);
  }
}

【讨论】:

  • 我想到了这一点,但它提出了自己的一系列问题。我用一个真实的例子更新了我的答案。对于我想要实现的目标,我只想在 current 和 newValue 不同时更新数据,并且只在它不同的情况下通知Listeners。我可以做注释掉的事情,但我希望我能够取消样板文件
  • 了解,这是一个很好的用例。在 Flutter 小部件生命周期方法中,有一个 didUpdateWidget 方法。
  • 这存在于小部件树之外
  • @HamishJohnson 我还没有这个问题的答案,equatable package 可能有助于减少一些更改比较代码。
猜你喜欢
  • 2013-09-25
  • 1970-01-01
  • 2012-01-06
  • 2013-09-27
  • 2021-04-11
  • 1970-01-01
  • 1970-01-01
  • 2011-02-10
  • 2020-04-01
相关资源
最近更新 更多