3

我想创建一个允许块更新其内容的属性。对于一个典型的变量(即不是自动合成的等),我会在声明前加上__block.

有没有办法制作一个能够被块更新的属性?

编辑:一些答案说只是使用属性设置器方法。我真正想做的是将对象添加到可变数组中,所以我真的不想创建一个新的可变数组并将其设置回使用setProperty:or.property =每次的属性。是否可以在没有所有这些内存分配的情况下修改属性?

4

4 回答 4

3

这不是正确的思考方式。您要修改具有属性的对象。因此,您捕获块中的对象,并调用其访问器 ( setFoo:) 来修改属性。


编辑:从各种编辑中,您可能会混淆 ObjC 对象的工作方式和 C++ 的工作方式。ObjC 只使用指向对象的指针,很少复制它们,并且缺乏const对象的概念(有不可变对象,但这只是因为它们没有修改器;你不能const像 C++ 中那样使用可变对象)。

__block只是意味着“这个变量(不是它指向的对象;这个实际变量)应该通过引用而不是通过值传递给块)。” 所以当我说:

__block id foo;

这意味着可以更改foo指针本身。foo它与指向的对象是否可以变异完全无关。这对全局或 ivar 没有意义。ivars 是隐式结构字段。当您说_ivar在块内时,编译器会将其隐式转换为self->_ivar然后捕获self. 它不捕获_ivar(因为这只是self结构的偏移量)。最好使用访问器来做同样的事情,因为它更明确你在做什么,你可以使用__weak这种方式。

于 2013-09-03T15:39:34.047 回答
3

__block用于声明块可能想要更改的局部变量。

属性也不是局部变量,当您只想向可变数组添加一些内容时,也不需要更改变量。变量没有改变,改变的是变量背后的对象状态。

于 2013-09-03T15:57:39.493 回答
2

当你想修改一个块中的变量时,你使用 __block;在您的情况下,您想要做的不是修改变量(它仍然指向相同的NSMutableArray),而只是向它发送一条消息(addObject:)。你不需要 __block 。

于 2013-09-03T16:02:16.023 回答
1

无需在@property声明中添加任何内容。因为它们可以被块访问和修改而没有任何麻烦。根据文档:

在块对象的代码主体中,可以用五种不同的方式处理变量。

您可以引用三种标准类型的变量,就像引用函数一样:

  1. 全局变量,包括静态局部变量
  2. 全局函数(在技术上不是变量)
  3. 封闭范围内的局部变量和参数

块还支持另外两种类型的变量:

  1. 在功能级别是__block变量。这些在块(和封闭范围)内是可变的,并且如果任何引用块被复制到堆中,它们就会被保留。
  2. const进口。

以下规则适用于块内使用的变量:

  1. 全局变量是可访问的,包括存在于封闭词法范围内的静态变量。
  2. 传递给块的参数是可访问的(就像函数的参数一样)。
  3. 封闭词法范围的本地堆栈(非静态)变量被捕获为const变量。
    它们的值取自程序中块表达式的位置。在嵌套块中,值是从最近的封闭范围捕获的。
  4. 使用存储修饰符声明的封闭词法范围的局部变量 __block由引用提供,因此是可变的。
    任何更改都反映在封闭词法范围中,包括在同一封闭词法范围内定义的任何其他块。
  5. 在块的词法范围内声明的局部变量,其行为与函数中的局部变量完全相同。
    块的每次调用都会提供该变量的新副本。这些变量又可以用作包含在块中的块中的常量或引用变量。
于 2013-09-03T15:44:06.417 回答