パッケージは、同じディレクトリに存在し、先頭に同じパッケージステートメントを持つGoファイルで構成されます。 プログラムをより洗練させるために、パッケージから追加の機能を含めることができます。 一部のパッケージはGo標準ライブラリから入手できるため、Goインストールとともにインストールされます。 その他は、Goのgo get
コマンドでインストールできます。 また、必要なpackageステートメントを使用してコードを共有するディレクトリと同じディレクトリにGoファイルを作成することにより、独自のGoパッケージを構築することもできます。
このチュートリアルでは、他のプログラミングファイル内で使用するGoパッケージを作成する方法を説明します。
前提条件
-
How To Install and Set Up a Local Programming Environment for Goシリーズのチュートリアルの1つに従って、Goプログラミング環境をセットアップします。 ローカルプログラミング環境のチュートリアルのステップ5に従ってGoワークスペースを作成します。 この記事の例と命名規則に従うには、最初のセクション「パッケージの作成とインポート」をお読みください。
-
GOPATHの知識を深めるには、記事Understanding the GOPATHをお読みください。
パッケージの作成とインポート
新しいパッケージを作成する前に、Goワークスペースにいる必要があります。 これは通常、gopath
の下にあります。 この例では、このチュートリアルではパッケージをgreet
と呼びます。 これを行うために、プロジェクトスペースの下のgopath
にgreet
というディレクトリを作成しました。 組織がgopherguides
であり、Githubをコードリポジトリとして使用しながら組織の下にgreet
パッケージを作成したい場合、ディレクトリは次のようになります。
└── $GOPATH
└── src
└── github.com
└── gopherguides
greet
ディレクトリはgopherguides
ディレクトリ内にあります。
└── $GOPATH
└── src
└── github.com
└── gopherguides
└── greet
最後に、ディレクトリに最初のファイルを追加できます。 パッケージ内のprimary
またはentry point
ファイルは、ディレクトリの名前にちなんで名付けられるのが一般的な方法と考えられています。 この場合、greet
ディレクトリ内にgreet.go
というファイルを作成します。
└── $GOPATH
└── src
└── github.com
└── gopherguides
└── greet
└── greet.go
ファイルを作成したら、プロジェクト間で再利用または共有したいコードを書き始めることができます。 この場合、Hello World
を出力するHello
という関数を作成します。
テキストエディタでgreet.go
ファイルを開き、次のコードを追加します。
greet.go
package greet
import "fmt"
func Hello() {
fmt.Println("Hello, World!")
}
この最初のファイルを分類しましょう。 各ファイルの最初の行には、作業しているpackage
の名前が必要です。 greet
パッケージを使用しているため、package
キーワードに続けてパッケージの名前を使用します。
package greet
これにより、ファイル内のすべてがgreet
パッケージの一部として扱われるようにコンパイラーに指示されます。
次に、import
ステートメントで使用する必要のある他のパッケージを宣言します。 このファイルでは、fmt
パッケージの1つだけを使用しています。
import "fmt"
最後に、関数Hello
を作成します。 fmt
パッケージを使用してHello, World!
を出力します。
func Hello() {
fmt.Println("Hello, World!")
}
greet
パッケージを作成したので、作成した他のパッケージで使用できます。 greet
パッケージを使用する新しいパッケージを作成しましょう。
example
という名前のパッケージを作成します。つまり、example
という名前のディレクトリが必要です。 gopherguides
組織でこのパッケージを作成すると、ディレクトリ構造は次のようになります。
└── $GOPATH
└── src
└── github.com
└── gopherguides
└── example
新しいパッケージのディレクトリができたので、エントリポイントファイルを作成できます。 これは実行可能プログラムになるため、エントリポイントファイルにmain.go
という名前を付けることをお勧めします。
└── $GOPATH
└── src
└── github.com
└── gopherguides
└── example
└── main.go
テキストエディタでmain.go
を開き、次のコードを追加してgreet
パッケージを呼び出します。
main.go
package main
import "github.com/gopherguides/greet"
func main() {
greet.Hello()
}
パッケージをインポートしているため、パッケージ名をドット表記で参照して関数を呼び出す必要があります。 Dot notationは、使用しているパッケージの名前と、そのパッケージ内で使用したいリソースの間にピリオド.
を置く方法です。 たとえば、greet
パッケージには、リソースとしてのHello
関数があります。 そのリソースを呼び出す場合は、greet.Hello()
のドット表記を使用します。
これで、ターミナルを開いてコマンドラインでプログラムを実行できます。
go run main.go
すると、次の出力が表示されます。
OutputHello, World!
パッケージで変数を使用する方法を確認するために、greet.go
ファイルに変数定義を追加しましょう。
greet.go
package greet
import "fmt"
var Shark = "Sammy"
func Hello() {
fmt.Println("Hello, World!")
}
次に、main.go
ファイルを開き、次の強調表示された行を追加して、fmt.Println()
関数のgreet.go
から変数を呼び出します。
main.go
package main
import (
"fmt"
"github.com/gopherguides/greet"
)
func main() {
greet.Hello()
fmt.Println(greet.Shark)
}
プログラムを再度実行したら:
go run main.go
次の出力が表示されます。
OutputHello, World!
Sammy
最後に、greet.go
ファイルでタイプも定義しましょう。 name
フィールドとcolor
フィールドを持つタイプOctopus
と、呼び出されたときにフィールドを出力する関数を作成します。
greet.go
package greet
import "fmt"
var Shark = "Sammy"
type Octopus struct {
Name string
Color string
}
func (o Octopus) String() string {
return fmt.Sprintf("The octopus's name is %q and is the color %s.", o.Name, o.Color)
}
func Hello() {
fmt.Println("Hello, World!")
}
main.go
を開いて、ファイルの最後にそのタイプのインスタンスを作成します。
main.go
package main
import (
"fmt"
"github.com/gopherguides/greet"
)
func main() {
greet.Hello()
fmt.Println(greet.Shark)
oct := greet.Octopus{
Name: "Jesse",
Color: "orange",
}
fmt.Println(oct.String())
}
oct := greet.Octopus
を使用してOctopus
タイプのインスタンスを作成すると、main.go
ファイルの名前空間内のタイプの関数とフィールドにアクセスできます。 これにより、greet
を呼び出さずに、最後の行にoct.String()
を書き込むことができます。 たとえば、greet
パッケージの名前を参照せずに、oct.Color
などのタイプフィールドの1つを呼び出すこともできます。
Octopus
タイプのString
メソッドは、fmt.Sprintf
関数を使用して文を作成し、returns
は結果、文字列を呼び出し元(この場合はメインプログラム)。
プログラムを実行すると、次の出力が表示されます。
go run main.go
OutputHello, World!
Sammy
The octopus's name is "Jesse" and is the color orange.
Octopus
にString
メソッドを作成することにより、カスタムタイプに関する情報を印刷するための再利用可能な方法が得られます。 将来このメソッドの動作を変更する場合は、この1つのメソッドのみを編集する必要があります。
エクスポートされたコード
呼び出したgreet.go
ファイル内のすべての宣言が大文字になっていることに気付いたかもしれません。 Goには、他の言語のようにpublic
、private
、またはprotected
修飾子の概念がありません。 外部の可視性は大文字で制御されます。 大文字で始まる型、変数、関数などは、現在のパッケージの外部で公開されています。 パッケージの外側に表示されるシンボルは、exported
と見なされます。
reset
と呼ばれる新しいメソッドをOctopus
に追加する場合、greet
パッケージ内から呼び出すことはできますが、main.go
ファイルから呼び出すことはできません。 t4)sパッケージ:
greet.go
package greet
import "fmt"
var Shark = "Sammy"
type Octopus struct {
Name string
Color string
}
func (o Octopus) String() string {
return fmt.Sprintf("The octopus's name is %q and is the color %s.", o.Name, o.Color)
}
func (o *Octopus) reset() {
o.Name = ""
o.Color = ""
}
func Hello() {
fmt.Println("Hello, World!")
}
main.go
ファイルからreset
を呼び出そうとすると、次のようになります。
main.go
package main
import (
"fmt"
"github.com/gopherguides/greet"
)
func main() {
greet.Hello()
fmt.Println(greet.Shark)
oct := greet.Octopus{
Name: "Jesse",
Color: "orange",
}
fmt.Println(oct.String())
oct.reset()
}
次のコンパイルエラーが表示されます。
Outputoct.reset undefined (cannot refer to unexported field or method greet.Octopus.reset)
Octopus
からreset
機能をexport
にするには、reset
のR
を大文字にします。
greet.go
package greet
import "fmt"
var Shark = "Sammy"
type Octopus struct {
Name string
Color string
}
func (o Octopus) String() string {
return fmt.Sprintf("The octopus's name is %q and is the color %s.", o.Name, o.Color)
}
func (o *Octopus) Reset() {
o.Name = ""
o.Color = ""
}
func Hello() {
fmt.Println("Hello, World!")
}
その結果、エラーが発生することなく、他のパッケージからReset
を呼び出すことができます。
main.go
package main
import (
"fmt"
"github.com/gopherguides/greet"
)
func main() {
greet.Hello()
fmt.Println(greet.Shark)
oct := greet.Octopus{
Name: "Jesse",
Color: "orange",
}
fmt.Println(oct.String())
oct.Reset()
fmt.Println(oct.String())
}
プログラムを実行する場合:
go run main.go
次の出力が表示されます。
OutputHello, World!
Sammy
The octopus's name is "Jesse" and is the color orange
The octopus's name is "" and is the color .
Reset
を呼び出すことにより、Name
およびColor
フィールドのすべての情報をクリアしました。 String
メソッドを呼び出すと、フィールドが空になっているため、Name
とColor
が通常表示される場所には何も出力されません。
結論
Goパッケージの作成は、他のGoファイルの作成と同じですが、別のディレクトリに配置すると、コードを分離して他の場所で再利用できます。 このチュートリアルでは、パッケージ内に定義を記述する方法を説明し、別のGoプログラミングファイル内でそれらの定義を使用する方法を示し、アクセスするためにパッケージを保持する場所のオプションについて説明しました。