2013-10-01 16 views
6

W moim kodu mam dużo kodu takich jak:jak przekazać blok jako argument makro w celu-c?

if (block) block(....) 

Więc chcę zdefiniować makro, coś jak

#define safetyCall(block, ...) if((block)) {block(##__VA_ARGS__)}; 

ale nie mogłem zmusić go do pracy. Dowolny pomysł?

+0

jeśli zgłoszę 'safetyCall (metoda, 0 newErr)' kompilator powiedzieć "utworzony wklejanie '(0' nieprawidłowy przerób znacznik" i „Oczekiwany '' po ekspresji " – jAckOdE

Odpowiedz

6

Nie potrzebują i ; potrzeby ## ruchu:

#define safetyCall(block, ...) if((block)) { block(__VA_ARGS__); } 
+0

działa doskonale, bardzo dziękuję! – jAckOdE

+0

btw, czym różni się od' __VA_ARGS__' i '## __ VA_ARGS__' – jAckOdE

+1

@jAckOdE Token' ##' służy do "stringify" jego argumentów (tj. Przekształcić je z 'x' w' "x" ').) – trojanfoe

2

Można uruchomić w kwestii, czy blok jest inline i zawiera kod, który posiada szereg oddzielonych przecinkami ciągi itp

Przykład.

safetyCall(^void() { 
    NSArray *foo = @[@"alice", "bob"]; 
}; 

kompilator skarżą się na " '' Oczekiwany ']' lub" i "Oczekiwany identyfikator lub '('"

Jednakże, jeśli zadeklarowałeś blok wbudowany jako oddzielny blok przed makrem, nie wygeneruje on błędu.

przykład:

void (^fooBlock)(void) = ^void() { 
    NSArray *foo = @[@"alice", @"bob"]; 
} 

safetyCall(fooBlock); 
+0

lub po prostu umieść blok w nawiasach – newacct

Powiązane problemy