Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

[インデックス 1492] ファイルの概要

このコミットは、Go言語の標準ライブラリstrconvパッケージ内の関数名を変更し、それらを外部から利用可能(エクスポート)にするためのものです。具体的には、atof64atoiftoa64といった小文字で始まる関数名が、Atof64AtoiFtoa64のように大文字で始まる名前に変更されています。これにより、これらの数値変換関数がGo言語の他のパッケージやユーザーアプリケーションから直接呼び出せるようになります。この変更は、Go言語の初期開発段階におけるAPIの整備の一環として行われました。

コミット

commit 8a7cbadbbe9768ccd7480bb11e35454e39ef2bdd
Author: Russ Cox <rsc@golang.org>
Date:   Thu Jan 15 17:22:17 2009 -0800

    convert strconv
    
    R=r
    DELTA=568  (0 added, 9 deleted, 559 changed)
    OCL=22898
    CL=22901

GitHub上でのコミットページへのリンク

https://github.com/golang/go/commit/8a7cbadbbe9768ccd7480bb11e35454e39ef2bdd

元コミット内容

convert strconv

R=r
DELTA=568  (0 added, 9 deleted, 559 changed)
OCL=22898
CL=22901

変更の背景

このコミットが行われた2009年1月は、Go言語がまだ一般に公開される前の初期開発段階でした。Go言語の設計思想の一つに「シンプルさ」と「明瞭さ」があり、その一環として、パッケージ外部に公開する(エクスポートする)識別子と、パッケージ内部でのみ使用する(エクスポートしない)識別子を明確に区別するルールが導入されました。

Go言語では、識別子(変数名、関数名、型名など)の最初の文字が大文字である場合、その識別子はパッケージ外部にエクスポートされ、他のパッケージからアクセス可能になります。一方、最初の文字が小文字である場合、その識別子はパッケージ内部でのみ使用され、外部からはアクセスできません。

strconvパッケージは、文字列と数値の相互変換を提供する非常に基本的なユーティリティパッケージであり、Go言語の他の多くの標準ライブラリパッケージやユーザーアプリケーションから利用されることが想定されていました。このコミット以前は、strconvパッケージ内の多くの変換関数が小文字で始まっており、パッケージ外部から直接利用することができませんでした。

この変更の背景には、strconvパッケージの機能がGo言語のコア機能として広く利用されるべきであるという認識と、Go言語の識別子の可視性に関する設計原則を早期に確立し、それに準拠させるという意図がありました。これにより、strconvパッケージの関数がGo言語のエコシステム全体で一貫した方法で利用できるようになり、開発者がより簡単に数値変換機能を利用できるようになりました。

前提知識の解説

Go言語における識別子の可視性(エクスポートルール)

Go言語には、識別子(変数、関数、型、メソッドなど)の可視性を制御するための明確なルールがあります。これは「エクスポートルール」と呼ばれ、非常にシンプルです。

  1. エクスポートされた識別子(Public):

    • 識別子の最初の文字が大文字で始まる場合、その識別子はエクスポートされます。
    • エクスポートされた識別子は、その識別子が定義されているパッケージの外部からアクセス可能です。つまり、他のパッケージからインポートして利用することができます。
    • 例: strconv.Atoi, fmt.Println, http.Server
  2. エクスポートされない識別子(Private/Internal):

    • 識別子の最初の文字が小文字で始まる場合、その識別子はエクスポートされません。
    • エクスポートされない識別子は、その識別子が定義されているパッケージの内部でのみアクセス可能です。パッケージの外部からは直接アクセスすることはできません。
    • 例: strconv.stringToDecimal, fmt.newPrinter, http.serve

このルールは、Go言語のAPI設計において非常に重要です。開発者は、パッケージの外部に公開すべき機能と、内部実装の詳細として隠蔽すべき機能を明確に区別することができます。これにより、パッケージのAPIがシンプルに保たれ、後方互換性を維持しやすくなります。

strconvパッケージの役割

strconvパッケージは、Go言語の標準ライブラリの一部であり、基本的なデータ型(整数、浮動小数点数、真偽値など)と文字列との間の変換機能を提供します。例えば、文字列を整数に変換したり(Atoi)、浮動小数点数を文字列に変換したり(Ftoa)する機能が含まれています。

このパッケージは、ファイルI/O、ネットワーク通信、コマンドライン引数の解析、JSONやXMLの処理など、文字列と数値の変換が頻繁に発生するあらゆる場面で利用されます。そのため、Go言語アプリケーション開発において非常に重要なユーティリティパッケージの一つです。

技術的詳細

このコミットの技術的な詳細は、主にGo言語の識別子の可視性ルールをstrconvパッケージに適用することに集約されます。

  1. 関数名の変更:

    • strconvパッケージ内で定義されていた、外部に公開されるべき関数(例: atof64, atoi, ftoa64, itoa64, atoui64など)の先頭文字が小文字から大文字に変更されました。
    • これにより、これらの関数はGo言語のコンパイラによってエクスポート可能と認識され、他のパッケージからstrconv.Atof64のようにドット記法で直接呼び出せるようになりました。
  2. 内部関数の維持:

    • strconvパッケージ内には、外部に公開する必要のないヘルパー関数や内部処理用の関数も存在します。これらの関数(例: stringToDecimal, decimalToFloatBits, trim, copy, digitZeroなど)は、引き続き小文字で始まる名前を維持しています。これは、それらがパッケージの内部実装の詳細であり、外部から直接アクセスされるべきではないという設計意図を反映しています。
  3. 呼び出し箇所の更新:

    • strconvパッケージの関数を利用していた他の標準ライブラリパッケージ(fmt, http, json, net, reflectなど)のコードも、新しい大文字で始まる関数名に合わせて修正されました。
    • 例えば、src/lib/fmt/format.goではstrconv.ftoa64strconv.Ftoa64に、src/lib/http/server.goではstrconv.atoistrconv.Atoiにそれぞれ変更されています。
    • テストファイル(例: src/lib/strconv/atof_test.go, src/lib/strconv/atoi_test.go)内のテストケースやヘルパー関数名も、同様に新しい命名規則に合わせて更新されています。これにより、テストコードも新しいAPIに準拠し、正しく機能することが保証されます。
  4. 影響範囲:

    • この変更は、Go言語の標準ライブラリ全体にわたる広範なリファクタリングの一部であり、Go言語のAPI設計の一貫性を高める上で重要なステップでした。
    • 特に、strconvパッケージは多くの場所で利用されるため、この変更はGo言語の初期のユーザーや開発者にとって、APIの安定性と予測可能性を向上させる上で大きな意味を持ちました。

このコミットは、単なる関数名の変更以上の意味を持ちます。それは、Go言語がその設計原則(特に可視性ルール)を初期段階から厳密に適用し、一貫性のあるAPIを提供しようとしていたことを示しています。これにより、Go言語のコードベースはより整理され、将来の拡張やメンテナンスが容易になりました。

コアとなるコードの変更箇所

このコミットのコアとなる変更は、src/lib/strconv/ディレクトリ内のファイル、およびstrconvパッケージの関数を呼び出している他の標準ライブラリパッケージ(src/lib/fmt/, src/lib/http/, src/lib/json/, src/lib/net/, src/lib/reflect/)における関数名の変更です。

具体的な変更パターンは以下の通りです。

  • src/lib/strconv/atof.go:

    • func atof64(s string) -> func Atof64(s string)
    • func atof32(s string) -> func Atof32(s string)
    • func atof(s string) -> func Atof(s string)
    • 内部関数(例: StringToDecimal -> stringToDecimal, DecimalToFloatBits -> decimalToFloatBitsなど)は小文字のまま維持されています。
  • src/lib/strconv/atoi.go:

    • func atoui64(s string) -> func Atoui64(s string)
    • func atoi64(s string) -> func Atoi64(s string)
    • func atoui(s string) -> func Atoui(s string)
    • func atoi(s string) -> func Atoi(s string)
    • func IntSize() -> func computeIntsize() (内部関数化)
  • src/lib/strconv/ftoa.go:

    • func ftoa32(f float32, ...) -> func Ftoa32(f float32, ...)
    • func ftoa64(f float64, ...) -> func Ftoa64(f float64, ...)
    • func ftoa(f float, ...) -> func Ftoa(f float, ...)
    • 内部関数(例: GenericFtoa -> genericFtoa, FmtB -> fmtBなど)は小文字のまま維持されています。
  • src/lib/strconv/itoa.go:

    • func itoa64(i int64) -> func Itoa64(i int64)
    • func itoa(i int) -> func Itoa(i int)
  • src/lib/strconv/decimal.go:

    • package type Decimal struct { ... } -> type decimal struct { ... } (型名も小文字化され、内部型に)
    • func NewDecimal(i uint64) -> func newDecimal(i uint64) (コンストラクタも内部関数に)
    • func Copy(dst []byte, src []byte) int -> func copy(dst []byte, src []byte) int
    • func DigitZero(dst []byte) int -> func digitZero(dst []byte) int
    • func Trim(a *Decimal) -> func trim(a *decimal)
    • const MaxShift -> const maxShift
    • type LeftCheat -> type leftCheat
    • var leftcheat -> var leftcheats
    • func PrefixIsLessThan -> func prefixIsLessThan
    • func RightShift -> func rightShift
    • func LeftShift -> func leftShift
    • func ShouldRoundUp -> func shouldRoundUp
    • func Max -> func max

これらの変更は、strconvパッケージのAPIをGo言語のエクスポートルールに準拠させ、外部から利用可能な関数を明確にするためのものです。

コアとなるコードの解説

このコミットにおけるコアとなるコードの変更は、Go言語の「エクスポートルール」をstrconvパッケージに適用した点にあります。

Go言語では、パッケージの外部からアクセスできる識別子(関数、変数、型など)は、その名前の最初の文字を大文字にする必要があります。逆に、パッケージ内部でのみ使用される識別子は、最初の文字を小文字にします。このルールは、Go言語のAPI設計の根幹をなすものであり、どの機能が公開APIの一部であるかを明確に示します。

strconvパッケージは、文字列と数値の変換という、Go言語のアプリケーション開発において非常に頻繁に利用される機能を提供します。したがって、このパッケージの主要な変換関数は、他のパッケージから容易に利用できるようにエクスポートされる必要があります。

このコミット以前は、strconvパッケージ内の多くの変換関数(例: atof64, atoi, ftoa64)が小文字で始まっていました。これは、それらがパッケージ内部でのみ使用されることを意図していたか、あるいはGo言語のエクスポートルールがまだ完全に確立されていなかった初期段階の名残である可能性があります。

このコミットでは、これらの関数名を大文字で始まるように変更することで、それらを正式にエクスポートされたAPIとして宣言しました。例えば、atof64(文字列をfloat64に変換)がAtof64に変更されたことで、import "strconv"した他のパッケージからstrconv.Atof64("123.45")のように直接呼び出すことが可能になりました。

同時に、strconvパッケージの内部実装で使用されるヘルパー関数やデータ構造(例: stringToDecimal, decimal, trimなど)は、引き続き小文字で始まる名前を維持しています。これは、これらの要素がパッケージの内部的な詳細であり、外部に公開する必要がないことを示しています。これにより、パッケージの内部実装が変更されても、外部APIの安定性が保たれるという利点があります。

この変更は、Go言語の標準ライブラリ全体の一貫性を高め、開発者がGo言語のAPIをより直感的に理解し、利用できるようにするための重要なステップでした。

関連リンク

参考にした情報源リンク

  • Go言語の公式リポジトリ: https://github.com/golang/go
  • Go言語の初期開発に関する議論やメーリングリストのアーカイブ (Go言語の歴史的背景を理解する上で有用):
  • Go言語の識別子の可視性に関する一般的なプログラミング記事やチュートリアル。