6022


コードはgistにあります．  
<https://gist.github.com/yuntan/86f715c0fa6f5aed5fea>

code1とcode2で`vd`のスコープが異なります．code1では関数スコープにしてあり，この場合`syscall.Syscall`は成功します．code2ではパッケージ変数になっていますが，この場合は`syscall.Syscall`はエラーを返します．

何が問題を引き起こしているのか教えていただきたいです．

go1.4 linux/amd64


CC BY-SA 3.0
2015-02-05T15:02:08.117
6018
2019-12-13T18:30:03.703
8099
question
linux go
go1.4 linux/amd64 システムコールの挙動が，引数のスコープにより異なる


以下と同じことが起こっていると思います。

_test.go_ : <https://play.golang.org/p/Qy4YaP8l-i>

[code]

    package main
    
    import "fmt"
    
    var vd = "Andy" // vd パッケージ変数は宣言された
    
    func main() {
        vd, _ := createName() // vd ローカル変数は宣言された
        fmt.Println("Main: " + vd)
        sayHello()
    }
    
    func createName() (string, error) {
        return "Bob", nil
    }
    
    func sayHello() {
        fmt.Println("sayHello: " + vd)
    }
    
[/code]

_Output_ :

[code]

    Main: Bob
    sayHello: Andy
    
[/code]

code2 では、パッケージ変数 `vd` と、ローカル変数 `vd` の２つの変数があります。パッケージ変数のほうの `vd`
は初期化されていませんよね。


CC BY-SA 3.0
2015-02-05T15:54:02.980
6022
2015-02-05T16:03:12.917
2015-02-05T16:03:12.917
4978
4978
6018
answer


golang
等、最近のプログラミング言語は[レキシカルスコープ](http://ja.wikipedia.org/wiki/%E9%9D%99%E7%9A%84%E3%82%B9%E3%82%B3%E3%83%BC%E3%83%97)を採用しています。  
code2 の main 内の vd は `:=` で宣言されていますので、main 関数のスコープ内で新しい同名の変数を宣言している事になります。  
この場合、main 内の vd に変更が加えられるだけで、外の vd には何も影響しません。  
例えるとこんな感じです。

<http://play.golang.org/p/MgW5pnvu6Y>

[code]

    package main
    
    import "fmt"
    
    var a = 1
    
    func main() {
        fmt.Println("test1", a) // 外のaが見える為、1
    
        a = 3 // 外のaを3に変えてしまう
    
        var a = 2
        fmt.Println("test2", a) // 真上のaが見える為、2
    
        foo()
    }
    
    func foo() {
        fmt.Println("test3", a) // 外のaが見える為、3
    }
    
[/code]

ただしレキシカルスコープを扱うプログラミング言語でも、途中で変数が宣言される場合の動きが異なる場合がありますので各言語の仕様を確認された方が良いと思います。  
例えば JavaScript では途中宣言は関数内全ての参照に影響します。

<http://jsfiddle.net/mattn/qb42qo3c/>

[code]

    var a = 1;
    
    function result(n, v) {
      document.getElementById(n).innerText = v;
    }
    
    function foo() {
      result("test3", a); // 外のaが見える為、1
    }
    
    (function() {
      // 関数内でaが宣言されているが初期化されていないので
      // undefined
      result("test1", a);
    
      a = 3; // 変更しても関数内のaが変わるだけ
    
      var a = 2;
      // 関数内のaが見えるので2
      result("test2", a);
    
      foo();
    })()
[/code]

[code]

    <div id="test1"></div>
    <div id="test2"></div>
    <div id="test3"></div>
[/code]

[code]

    var a = 1;
    
    function result(n, v) {
        document.getElementById(n).innerText = v;
    }
    
    function foo() {
        result("test3", a); // 外のaが見える為、1
    }
    
    (function() {
        // 関数内でaが宣言されているが初期化されていないので
        // undefined
        result("test1", a);
    
        a = 3; // 変更しても関数内のaが変わるだけ
    
        var a = 2;
        // 関数内のaが見えるので2
        result("test2", a);
    
        foo();
    })()
    
[/code]


CC BY-SA 4.0
2015-02-05T16:32:50.427
6023
2019-12-13T18:30:03.703
2019-12-13T18:30:03.703
32986
440
6018
answer