計算機科学のブログ

有限体 有限集合の定義 Goによる有限体の構成 要素 等号と不等号

プログラミング・ビットコイン ―ゼロからビットコインをプログラムする方法 (Jimmy Song(著)、中川 卓俊(監修)、住田 和則(監修)、中村 昭雄(監修)、星野 靖子(翻訳)、オライリー・ジャパン)の1章(有限体)、1.3(有限集合の定義)、1.3.1(Pythonによる有限体の構成)、練習問題1の解答をPythonではなくGoで求めてみる。

コード

ecc.go

// Package ecc (Elliptic Curve Cryptography, 楕円曲線暗号)
package ecc

import "fmt"

// FieldElement 有限体の要素
type FieldElement struct {
	Num   int
	Prime int
}

// NewFieldElement ...
func NewFieldElement(n, p int) (FieldElement, error) {
	if n >= p || n < 0 {
		return FieldElement{-1, -1}, fmt.Errorf("%v not in field range 0 to %v", n, p-1)
	}
	return FieldElement{n, p}, nil
}

// Eq ...
func Eq(fe1, fe2 FieldElement) bool {
	if fe1.Num == -1 || fe2.Num == -1 {
		return false
	}
	return fe1.Num == fe2.Num && fe1.Prime == fe2.Prime
}

// Ne ...
func Ne(fe1, fe2 FieldElement) bool {
	return !Eq(fe1, fe2)
}

ecc_test.go

package ecc

import "testing"

func TestNewFieldElementEq(t *testing.T) {
	a, _ := NewFieldElement(7, 13)
	b, _ := NewFieldElement(6, 13)
	got := Eq(a, b)
	if got {
		t.Errorf("Eq(%v, %v) got %v, want false", a, b, got)
	}
	got = Eq(a, a)
	if !got {
		t.Errorf("Eq(%v, %v) got %v, want true", a, a, got)
	}
}
func TestNewFieldElementNe(t *testing.T) {
	a, _ := NewFieldElement(7, 13)
	b, _ := NewFieldElement(6, 13)
	got := Ne(a, b)
	if !got {
		t.Errorf("Ne(%v, %v) got %v, want true", a, b, got)
	}
	got = Ne(a, a)
	if got {
		t.Errorf("Ne(%v, %v) got %v, want false", a, a, got)
	}
}

入出力結果

% go test
# bitcoin/ecc [bitcoin/ecc.test]
./ecc_test.go:6:10: undefined: NewFieldElement
./ecc_test.go:7:10: undefined: NewFieldElement
./ecc_test.go:8:9: undefined: Eq
./ecc_test.go:12:8: undefined: Eq
FAIL	bitcoin/ecc [build failed]
% go test
PASS
ok  	bitcoin/ecc	0.110s
% go test
# bitcoin/ecc [bitcoin/ecc.test]
./ecc_test.go:20:9: undefined: Ne
FAIL	bitcoin/ecc [build failed]
% go test
PASS
ok  	bitcoin/ecc	0.213s
%