Docs clarification: local static variable (#8381)

This commit is contained in:
Roman Frołow 2021-06-23 07:45:36 +02:00 committed by GitHub
parent da063ebd96
commit ce3679aa45
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

View File

@ -258,7 +258,7 @@ pub fn main() !void {
<p>
The code sample begins by adding Zig's Standard Library to the build using the {#link|@import#} builtin function.
The {#syntax#}@import("std"){#endsyntax#} function call creates a structure to represent the Standard Library.
The code then makes a {#link|top-level declaration|Global Variables#} of a
The code then {#link|declares|Container level Variables#} a
{#link|constant identifier|Assignment#}, named <code>std</code>, for easy access to
<a href="https://github.com/ziglang/zig/wiki/FAQ#where-is-the-documentation-for-the-zig-standard-library">Zig's standard library</a>.
</p>
@ -802,7 +802,7 @@ const hello_world_in_c =
const x = 1234;
fn foo() void {
// It works at global scope as well as inside functions.
// It works at file scope as well as inside functions.
const y = 5678;
// Once assigned, an identifier cannot be changed.
@ -872,18 +872,18 @@ test "init with undefined" {
{#syntax#}var{#endsyntax#} when declaring a variable. This causes less work for both
humans and computers to do when reading code, and creates more optimization opportunities.
</p>
{#header_open|Global Variables#}
{#header_open|Container Level Variables#}
<p>
Global variables are considered to be a top level declaration, which means that they are
order-independent and lazily analyzed. The initialization value of global variables is implicitly
{#link|comptime#}. If a global variable is {#syntax#}const{#endsyntax#} then its value is
Container level variables have static lifetime and are order-independent and lazily analyzed.
The initialization value of container level variables is implicitly
{#link|comptime#}. If a container level variable is {#syntax#}const{#endsyntax#} then its value is
{#syntax#}comptime{#endsyntax#}-known, otherwise it is runtime-known.
</p>
{#code_begin|test|global_variables#}
{#code_begin|test|container_level_variables#}
var y: i32 = add(10, x);
const x: i32 = add(12, 34);
test "global variables" {
test "container level variables" {
try expect(x == 46);
try expect(y == 56);
}
@ -896,27 +896,51 @@ const std = @import("std");
const expect = std.testing.expect;
{#code_end#}
<p>
Global variables may be declared inside a {#link|struct#}, {#link|union#}, or {#link|enum#}:
Container level variables may be declared inside a {#link|struct#}, {#link|union#}, or {#link|enum#}:
</p>
{#code_begin|test|namespaced_global#}
{#code_begin|test|namespaced_container_level_variable#}
const std = @import("std");
const expect = std.testing.expect;
test "namespaced global variable" {
test "namespaced container level variable" {
try expect(foo() == 1235);
try expect(foo() == 1236);
}
const S = struct {
var x: i32 = 1234;
};
fn foo() i32 {
const S = struct {
var x: i32 = 1234;
};
S.x += 1;
return S.x;
}
{#code_end#}
{#header_close#}
{#header_open|Static Local Variables#}
<p>
The {#syntax#}extern{#endsyntax#} keyword can be used to link against a variable that is exported
It is also possible to have local variables with static lifetime by using containers inside functions.
</p>
{#code_begin|test|static_local_variable#}
const std = @import("std");
const expect = std.testing.expect;
test "static local variable" {
expect(foo() == 1235);
expect(foo() == 1236);
}
fn foo() i32 {
const S = struct {
var x: i32 = 1234;
};
S.x += 1;
return S.x;
}
{#code_end#}
<p>
The {#syntax#}extern{#endsyntax#} keyword or {#link|@extern#} builtin function can be used to link against a variable that is exported
from another object. The {#syntax#}export{#endsyntax#} keyword or {#link|@export#} builtin function
can be used to make a variable available to other objects at link time. In both cases,
the type of the variable must be C ABI compatible.
@ -948,7 +972,7 @@ fn testTls(context: void) void {
}
{#code_end#}
<p>
For {#link|Single Threaded Builds#}, all thread local variables are treated as {#link|Global Variables#}.
For {#link|Single Threaded Builds#}, all thread local variables are treated as regular {#link|Container Level Variables#}.
</p>
<p>
Thread local variables may not be {#syntax#}const{#endsyntax#}.
@ -2467,7 +2491,7 @@ test "dot product" {
try expect(Vec3.dot(v1, v2) == 0.0);
}
// Structs can have global declarations.
// Structs can have declarations.
// Structs can have 0 fields.
const Empty = struct {
pub const PI = 3.14;
@ -5684,7 +5708,7 @@ test "@intToPtr for pointer to zero bit type" {
{#header_open|usingnamespace#}
<p>
{#syntax#}usingnamespace{#endsyntax#} is a top level declaration that imports all the public declarations of
{#syntax#}usingnamespace{#endsyntax#} is a declaration that imports all the public declarations of
the operand, which must be a {#link|struct#}, {#link|union#}, or {#link|enum#}, into the current scope:
</p>
{#code_begin|test|usingnamespace#}
@ -5692,6 +5716,19 @@ usingnamespace @import("std");
test "using std namespace" {
try testing.expect(true);
}
{#code_end#}
<p>
{#syntax#}usingnamespace{#endsyntax#} can also be used in containers:
</p>
{#code_begin|test|usingnamespace_inside_struct#}
test "using namespace inside struct" {
const L = struct {
usingnamespace struct {
pub fn f() void {}
};
};
L.f();
}
{#code_end#}
<p>
@ -6044,7 +6081,7 @@ test "fibonacci" {
</p>
<p>
In the global scope (outside of any function), all expressions are implicitly
At container level (outside of any function), all expressions are implicitly
{#syntax#}comptime{#endsyntax#} expressions. This means that we can use functions to
initialize complex static data. For example:
</p>
@ -8529,7 +8566,7 @@ fn List(comptime T: type) type {
}
{#code_end#}
<p>
When {#syntax#}@This(){#endsyntax#} is used at global scope, it returns a reference to the
When {#syntax#}@This(){#endsyntax#} is used at file scope, it returns a reference to the
struct that corresponds to the current file.
</p>
{#header_close#}
@ -8744,7 +8781,7 @@ pub fn build(b: *Builder) void {
{#header_open|Single Threaded Builds#}
<p>Zig has a compile option <code>--single-threaded</code> which has the following effects:</p>
<ul>
<li>All {#link|Thread Local Variables#} are treated as {#link|Global Variables#}.</li>
<li>All {#link|Thread Local Variables#} are treated as regular {#link|Container Level Variables#}.</li>
<li>The overhead of {#link|Async Functions#} becomes equivalent to function call overhead.</li>
<li>The {#syntax#}@import("builtin").single_threaded{#endsyntax#} becomes {#syntax#}true{#endsyntax#}
and therefore various userland APIs which read this variable become more efficient.