Go言語(golang)のstruct

※当サイトではアフィリエイト広告を利用しています

目次

Go言語(golang)のstruct

structの使い方を説明します。Tour of Goを参考にしています。

複数のデータ型をまとめて、ひとつの新しいデータ型を作成できるのがstructです。構造体とも呼ばれます。

Go言語(golang)のstructの使い方

Golangのstructは、関連する異なるデータ型をまとめ、新しい複合データ型を作成するための仕組みです。structはフィールドから構成され、これによって異なるデータ型の要素をひとまとめにすることができます。以下は基本的なstructの使用例です。

package main

import "fmt"

// Person structの定義
type Person struct {
    FirstName string
    LastName  string
    Age       int
}

func main() {
    // Person型の変数を作成
    person1 := Person{
        FirstName: "John",
        LastName:  "Doe",
        Age:       30,
    }

    // フィールドへのアクセス
    fmt.Println("First Name:", person1.FirstName)
    fmt.Println("Last Name:", person1.LastName)
    fmt.Println("Age:", person1.Age)

    // フィールドの更新
    person1.Age = 31
    fmt.Println("Updated Age:", person1.Age)
}

結果

First Name: John
Last Name: Doe
Age: 30
Updated Age: 31

この例では、Personという名前のstructFirstNameLastNameAgeという3つのフィールドを持っています。これを使ってperson1という変数を作成し、各フィールドにアクセスしています。

Golangのstructの特徴:

  1. フィールドの初期化: Person型の変数を作成する際、フィールドに初期値を指定することができます。また、初期化時に一部のフィールドだけを指定し、残りはゼロ値が設定されます。
  2. フィールドの更新: 作成したstructのフィールドは、後から更新することができます。
  3. メソッドの追加: structにはメソッド(関数)を関連付けることも可能です。これにより、特定のデータ型に対する操作をカプセル化できます。
// メソッドの追加
func (p Person) FullName() string {
    return p.FirstName + " " + p.LastName
}

// ...

// メソッドの呼び出し
fullName := person1.FullName()
fmt.Println("Full Name:", fullName)

structは、関連するデータをまとめ、プログラムの構造を効果的に表現するために使用されます。

structの使い所

structは、異なるデータ型の要素をまとめ、新しい複合データ型を作成するための有用な仕組みです。以下は、structの使いどころや一般的な利用例です。

データのまとめ

structは関連するデータをまとめるのに便利です。たとえば、ユーザーや商品の情報など、1つのエンティティに関連する異なる属性をまとめるのに使います。

type User struct {
    ID       int
    Username string
    Email    string
    // 他にも様々な属性がここに含まれる可能性がある
}

関数におけるパラメータのまとめ

複数の関連するパラメータを1つの引数として受け渡す場合、structを使用して関連するデータをまとめることができます。

type Point struct {
    X, Y int
}

func move(p Point, dx, dy int) Point {
    p.X += dx
    p.Y += dy
    return p
}

メソッドの追加

structには関数(メソッド)を関連付けることができます。これにより、特定のデータ型に対する操作をカプセル化し、よりオブジェクト指向的なアプローチを取ることができます。

type Circle struct {
    Radius float64
}

func (c Circle) Area() float64 {
    return 3.14 * c.Radius * c.Radius
}

JSONデータの表現

structはJSONデータの構造を表現するのにも適しています。JSONデータは一般的にキーと値のペアの集合であり、structはそのようなデータ構造を表現するのに適しています。

type Person struct {
    Name  string `json:"name"`
    Age   int    `json:"age"`
    Email string `json:"email"`
}

データベースとの対話

データベースとの対話においても、行やテーブルの構造を表現するためにstructが使用されます。ORM(Object-Relational Mapping)と組み合わせて、データベースとの対話を容易にします。

これらはstructを使用する典型的な場面の一部です。一般的に、関連する属性をグループ化してコードを整理し、可読性を向上させるために使われます。

structの注意点

ゼロ値

structを初期化しない場合、そのstructの各フィールドはゼロ値で初期化されます。これは、数値型の場合は0、文字列型の場合は空文字列などです。初期化が重要な場合は、適切に初期化するか、コンストラクタを使用するようにしましょう。

type Point struct {
    X, Y int
}

// 初期化なしで宣言
var p Point
fmt.Println(p.X, p.Y) // ゼロ値が表示される

ポインタと値の挙動

structを関数に渡すとき、ポインタか値かによって挙動が異なります。ポインタを使ってstructを渡すと、関数内での変更が呼び出し元に影響しますが、値を使って渡すとコピーが作成され、関数内での変更が呼び出し元には反映されません。

type Person struct {
    Name string
}

func modifyName(p Person) {
    p.Name = "John"
}

func modifyNameWithPointer(p *Person) {
    p.Name = "John"
}

// ...

person := Person{Name: "Alice"}

modifyName(person)
fmt.Println(person.Name) // Alice (変更が反映されない)

modifyNameWithPointer(&person)
fmt.Println(person.Name) // John (変更が反映される)

Immutableなフィールド

Golangのstructのフィールドは公開(大文字で始まる)または非公開(小文字で始まる)にできます。非公開フィールドは他のパッケージからアクセスできないため、変更不可(Immutable)と見なせます。一方で、公開フィールドには直接アクセスできるため、意図しない変更を防ぐためにはメソッドを経由してアクセスすることが望ましいです。

type Car struct {
    model string // 非公開フィールド
}

func (c *Car) GetModel() string {
    return c.model
}

// ...

car := Car{model: "Toyota"}

// 直接アクセスするとエラーになる
// fmt.Println(car.model) // エラー

// メソッドを経由してアクセス
fmt.Println(car.GetModel()) // Toyota

これらのポイントを考慮すると、より効果的かつ安全にstructを使用できます。特にデータの変更が制御されるべき場面では、ポインタを使ってstructを渡すことがより適しています。

よかったらシェアしてね!
  • URLをコピーしました!
  • URLをコピーしました!

この記事を書いた人

テック企業でプレイングマネージャーをしている Jun です。プログラミングの基礎をはじめ、組織やマネジメントについてブログを書いています。ハードスキル、ソフトスキルどちらも磨きたい方を対象にしています。一緒に学んで人生を楽しくしていきましょう!

目次