Jaki jest sens używania {
i }
w case
oświadczeniu? Zwykle, bez względu na to, ile wierszy jest w case
instrukcji, wszystkie wiersze są wykonywane. Czy to tylko reguła dotycząca starszych / nowszych kompilatorów, czy też coś za tym stoi?
int a = 0;
switch (a) {
case 0:{
std::cout << "line1\n";
std::cout << "line2\n";
break;
}
}
i
int a = 0;
switch (a) {
case 0:
std::cout << "line1\n";
std::cout << "line2\n";
break;
}
c++
switch-statement
mahmood
źródło
źródło
switch
słowem kluczowym, aw drugim przykładzie załączone instrukcje są wcięte tylko raz. Zwróć uwagę na niewygodne wcięcie o cztery spacje pobreak;
.statement
. W C ++ możesz (jednym ze składników kategorii syntaktycznejstatement
jestdeclaration statement
).Odpowiedzi:
{}
Oznacza nowy blok zakresu .Rozważmy następujący bardzo wymyślny przykład:
Pojawi się błąd kompilatora, ponieważ
x
jest już zdefiniowany w zakresie.Oddzielenie ich do ich własnego podzakresu eliminuje potrzebę deklarowania
x
poza instrukcją switch.źródło
TL; DR
Jedynym sposobem, w jaki można zadeklarować zmienną z intializatorem lub jakimś nietrywialnym obiektem wewnątrz przypadku, jest wprowadzenie zakresu blokowego przy użyciu
{}
lub innej struktury kontrolnej, która ma własny zakres, jak pętla lub instrukcja if .Krwawe szczegóły
Widzimy, że przypadki są po prostu etykietowanymi instrukcjami, takimi jak etykiety używane z instrukcją goto ( jest to omówione w szkicu standardu C ++ w sekcji 6.1 Oznakowane instrukcje ) i widzimy z sekcji
6.7
paragraf 3, że przeskakiwanie do deklaracji jest w wielu przypadkach niedozwolone , w tym te z inicjalizacją:i podaje ten przykład:
Zauważ, że są tutaj pewne subtelności, możesz przeskoczyć poza deklarację skalarną , która nie ma inicjalizacji, na przykład:
jest całkowicie poprawny ( przykład na żywo ). Oczywiście, jeśli chcesz zadeklarować tę samą zmienną w każdym przypadku, każda z nich będzie potrzebować własnego zakresu, ale działa to tak samo również poza instrukcjami switch , więc nie powinno to być dużym zaskoczeniem.
Jeśli chodzi o uzasadnienie niedopuszczania do przeskoczenia po inicjalizacji, raport defektu 467, chociaż obejmuje nieco inny problem, zapewnia rozsądny argument dla zmiennych automatycznych :
Prawdopodobnie bardziej interesujące jest przyjrzenie się przypadkowi, w którym rozszerza się zakres w ramach przełączania na wiele przypadków, najsłynniejszym tego przykładem jest prawdopodobnie urządzenie Duffa, które wyglądałoby mniej więcej tak:
źródło
Jest to nawyk, który pozwala na wstrzykiwanie deklaracji zmiennych z wynikowym destruktorem (lub konfliktami zakresu) do
case
klauzul. Innym sposobem patrzenia na to jest to, że piszą w języku, który chcieliby mieć, w którym cała kontrola przepływu składa się z bloków, a nie sekwencji instrukcji.źródło
Sprawdź to podstawowe ograniczenie kompilatora, a zaczniesz się zastanawiać, co się dzieje:
To spowoduje błąd:
Chociaż ten nie będzie:
źródło
Używanie nawiasów w przełączniku oznacza nowy blok zakresu, jak powiedział Rotem.
Ale może to być również dla jasności podczas czytania. Aby wiedzieć, gdzie kończy się sprawa, ponieważ możesz mieć w niej warunkową przerwę.
źródło
Powody mogą być następujące:
źródło