Namespaces
Variants
Views
Actions

Difference between revisions of "cpp/language/goto"

From cppreference.com
< cpp‎ | language
m (navbar try)
(expand)
Line 2: Line 2:
 
{{cpp/language/statements/navbar}}
 
{{cpp/language/statements/navbar}}
  
Transfers control to a new location.
+
Transfers control unconditionally.
  
Used when it is otherwise impossible to transfer control to the desired location using conventional constructs.
+
Used when it is otherwise impossible to transfer control to the desired location using other statements.
  
 
===Syntax===
 
===Syntax===
Line 14: Line 14:
 
===Explanation===
 
===Explanation===
  
The goto statement transfers control to the location specified by {{sparam|label}}. The goto statement must be in the same function as the {{sparam|label}} it is referring. If goto statement transfers control backwards, all objects that are not yet initialized at the {{sparam|label}} are destructed. It is illegal to transfer control forwards if doing so would skip initialization of an object.
+
The goto statement transfers control to the location specified by {{sparam|label}}. The goto statement must be in the same function as the {{sparam|label}} it is referring, it may appear before or after the label.
{{todo|special rules for skipping PODs}}
+
 
 +
If transfer of control exits the scope of any automatic variables (e.g. by jumping backwards to a point before the declarations of such variables or by jumping forward out of a compound statement where the variables are scoped), the destructors are called for all variables whose scope was exited, in the order opposite to the order of their construction.
 +
 
 +
If transfer of control enters the scope of any automatic variables (e.g. by jumping forward over a declaration statement), the program is ill-formed (cannot be compiled), unless all variables whose scope is entered have
 +
@1@ scalar types declared without initializers
 +
@2@ class types with trivial default constructors and trivial destructors declared without initializers
 +
@3@ cv-qualified versions of one of the above
 +
@4@ arrays of one of the above
 +
 
 +
(Note: the same rules apply to all forms of transfer of control)
 +
 
 
===Keywords===
 
===Keywords===
  
Line 26: Line 36:
  
 
struct Object {
 
struct Object {
 +
    // non-trivial destructor
 
     ~Object() { std::cout << "d"; }
 
     ~Object() { std::cout << "d"; }
 
};
 
};
 +
 +
struct Trivial {
 +
    double d1;
 +
    double d2;
 +
}; // trivial ctor and dtor
  
 
int main()
 
int main()
Line 33: Line 49:
 
     int a = 10;
 
     int a = 10;
 
      
 
      
     //loop using goto
+
     // loop using goto
 
label:
 
label:
 
     Object obj;
 
     Object obj;
Line 40: Line 56:
  
 
     if (a != 0) {
 
     if (a != 0) {
         goto label;  //causes obj to be destructed
+
         goto label;  // jumps out of scope of obj, calls obj destructor
 
     }
 
     }
 
     std::cout << '\n';
 
     std::cout << '\n';
  
     //get out of multi-level loop easily
+
     // goto can be used to leave a multi-level loop easily
 
     for (int x = 0; x < 3; x++) {
 
     for (int x = 0; x < 3; x++) {
 
         for (int y = 0; y < 3; y++) {
 
         for (int y = 0; y < 3; y++) {
Line 56: Line 72:
 
     std::cout << '\n';
 
     std::cout << '\n';
  
     return 0;  //causes obj to be destructed
+
     goto label2; // jumps into the scope of n and t
 +
    int n; // no initializer
 +
    Trivial t; // trivial ctor/dtor, no initializer
 +
// int x = 1; // error: has initializer
 +
//  Object obj2; // error: non-trivial dtor
 +
label2:
 +
 
 +
    {
 +
        Object obj3;
 +
        goto label3; // jumps forward, out of scope of obj3
 +
    }
 +
label3: ;
 +
 
 
}
 
}
 
  | output=
 
  | output=
 
10 d8 d6 d4 d2
 
10 d8 d6 d4 d2
(0;0) (0;1) (0;2) (1;0) (1;1) (1;2)
+
(0;0)  
d
+
(0;1)  
 +
(0;2)  
 +
(1;0)  
 +
(1;1)  
 +
(1;2)  
 +
 
 +
dd
 
}}
 
}}
  

Revision as of 13:46, 1 May 2013

 
 
C++ language
General topics
Flow control
Conditional execution statements
if
Iteration statements (loops)
for
range-for (C++11)
Jump statements
goto - return
Functions
Function declaration
Lambda function expression
inline specifier
Dynamic exception specifications (until C++17*)
noexcept specifier (C++11)
Exceptions
Namespaces
Types
Specifiers
const/volatile
decltype (C++11)
auto (C++11)
constexpr (C++11)
consteval (C++20)
constinit (C++20)
Storage duration specifiers
Initialization
Expressions
Alternative representations
Literals
Boolean - Integer - Floating-point
Character - String - nullptr (C++11)
User-defined (C++11)
Utilities
Attributes (C++11)
Types
typedef declaration
Type alias declaration (C++11)
Casts
Memory allocation
Classes
Class-specific function properties
explicit (C++11)
static

Special member functions
Templates
Miscellaneous
 
 

Transfers control unconditionally.

Used when it is otherwise impossible to transfer control to the desired location using other statements.

Contents

Syntax

Template:sparam(optional) goto Template:sparam ;

Explanation

The goto statement transfers control to the location specified by Template:sparam. The goto statement must be in the same function as the Template:sparam it is referring, it may appear before or after the label.

If transfer of control exits the scope of any automatic variables (e.g. by jumping backwards to a point before the declarations of such variables or by jumping forward out of a compound statement where the variables are scoped), the destructors are called for all variables whose scope was exited, in the order opposite to the order of their construction.

If transfer of control enters the scope of any automatic variables (e.g. by jumping forward over a declaration statement), the program is ill-formed (cannot be compiled), unless all variables whose scope is entered have

1) scalar types declared without initializers
2) class types with trivial default constructors and trivial destructors declared without initializers
3) cv-qualified versions of one of the above
4) arrays of one of the above

(Note: the same rules apply to all forms of transfer of control)

Keywords

goto

Example

#include <iostream>
 
struct Object {
    // non-trivial destructor
    ~Object() { std::cout << "d"; }
};
 
struct Trivial {
    double d1;
    double d2;
}; // trivial ctor and dtor
 
int main()
{
    int a = 10;
 
    // loop using goto
label:
    Object obj;
    std::cout << a << " ";
    a = a - 2;
 
    if (a != 0) {
        goto label;  // jumps out of scope of obj, calls obj destructor
    }
    std::cout << '\n';
 
    // goto can be used to leave a multi-level loop easily
    for (int x = 0; x < 3; x++) {
        for (int y = 0; y < 3; y++) {
            std::cout << "(" << x << ";" << y << ") " << '\n';
            if (x + y >= 3) {
                goto endloop;
            }
        }
    }
endloop:
    std::cout << '\n';
 
    goto label2; // jumps into the scope of n and t
    int n; // no initializer
    Trivial t; // trivial ctor/dtor, no initializer
//  int x = 1; // error: has initializer
//  Object obj2; // error: non-trivial dtor
label2:
 
    {
        Object obj3;
        goto label3; // jumps forward, out of scope of obj3
    }
label3: ;
 
}

Output:

10 d8 d6 d4 d2
(0;0) 
(0;1) 
(0;2) 
(1;0) 
(1;1) 
(1;2) 
 
dd