Sí, esto es seguro. No necesita hacer una copia. En el momento en que -[Foo doSomethingElseWithBlock:]
hace una copia de tu bloque literal, copiará el bloque interno al montón.
Escribí un código de prueba para comprobarme que esto sucede; vea cómo printer
(usado solo en block1
) se copia de la pila al montón en el momento en que se llama al Block_copy(block2)
.
#include <Block.h>
#include <dispatch/dispatch.h>
#include <stdio.h>
typedef void (^void_block)();
class ScopedPrinter {
public:
ScopedPrinter() {
printf("construct %p\n", this);
}
ScopedPrinter(const ScopedPrinter& other) {
printf("copy %p <- %p\n", this, &other);
}
~ScopedPrinter() {
printf("destroy %p\n", this);
}
};
void_block invoke(void_block other) {
printf("other %p\n", (void*)other);
void_block block2 = ^{
printf("other %p\n", (void*)other);
other();
};
printf("block2 created\n");
block2 = Block_copy(block2);
printf("block2 copied\n");
return block2;
}
void_block make_block() {
ScopedPrinter printer;
printf("printer created\n");
void_block block1 = ^{
printf("block1 %p\n", &printer);
};
printf("block1 created\n");
return invoke(block1);
}
int main() {
void_block block = make_block();
block();
Block_release(block);
return 0;
}
Transcripción:
construct 0x7fff6a23fa70
printer created
copy 0x7fff6a23fa50 <- 0x7fff6a23fa70
block1 created
other 0x7fff6a23fa30
block2 created
copy 0x10a700970 <- 0x7fff6a23fa50
block2 copied
destroy 0x7fff6a23fa50
destroy 0x7fff6a23fa70
other 0x10a700950
block1 0x10a700970
destroy 0x10a700970
Quizás quiso probarlo? –
Mi aplicación no es particularmente ejecutable en este punto, entonces no. Encontré esto: http://clang.llvm.org/docs/Block-ABI-Apple.txt que dice "Los bloques pueden contener expresiones literales de bloque. Todas las variables utilizadas dentro de los bloques internos se importan a todo el bloque que lo rodea. alcances incluso si las variables no se usan. Esto incluye las importaciones de const y las variables __block ". Sin embargo, en este caso es un literal de bloque que contiene un bloque, no el orden dado allí. –