golang fmt包Stringer接口測試實例

Stringer接口結構如下:

type Stringer interface {
    String() string
}

作用:

實現了Stringer接口的類型(即有String方法),定義了該類型值的原始顯示。當採用任何接受字符的verb(%v %s %q %x %X)動作格式化一個操作數時,或者被不使用格式字符串如Print函數打印操作數時,會調用String方法來生成輸出的文本。

int類型實現String()方法

type intExtend int

func (s intExtend) String() string {
	return fmt.Sprintf("%d extend", int(s))
}

var i int = 5
var ie intExtend = 5
fmt.Printf("%s\n", i) 	// %!s(int=5)
fmt.Printf("%s\n", ie)	// 5 extend

fmt.Printf("%q\n", i)	// \x05
fmt.Printf("%q\n", ie)	// 5 extend

fmt.Printf("%v\n", i)	// 5
fmt.Printf("%v\n", ie)	// 5 extend

fmt.Printf("%x\n", i)	// 5 (數值的16進制)
fmt.Printf("%x\n", ie)	// 3520657874656e64 ( 等同 fmt.Printf("%x\n","5 extend") )

fmt.Printf("%X\n", i)	// 5 (數值的16進制)
fmt.Printf("%X\n", ie)	// 3520657874656e64 ( 等同 fmt.Printf("%X\n","5 extend") )

string類型實現String()方法

type stringExtend string

func (s stringExtend) String() string {
	//注意 需要用string(s)強制轉化下類型,否則會無限遞歸
	return fmt.Sprintf("%s extend", string(s))
}

var s string = "string"
var se stringExtend = "string"
fmt.Printf("%s\n", s)  // string
fmt.Printf("%s\n", se) // string extend

fmt.Printf("%q\n", s)  // "string"
fmt.Printf("%q\n", se) // "string extend"

fmt.Printf("%v\n", s)  // string
fmt.Printf("%v\n", se) // string extend

fmt.Printf("%x\n", s)  // 737472696e67 ( 等同 fmt.Printf("%x\n","string") )
fmt.Printf("%x\n", se) // 737472696e6720657874656e64 ( 等同 fmt.Printf("%x\n","string extend") )

fmt.Printf("%X\n", s)  // 737472696E67 ( 等同 fmt.Printf("%X\n","string") )
fmt.Printf("%X\n", se) // 737472696E6720657874656E64 ( 等同 fmt.Printf("%X\n","string extend") )

struct類型實現String()方法

type AnimalSelfDefine struct {
	Name string
	Age  int
}

// 實現Stringer接口的方法
func (a AnimalSelfDefine) String() string {
	return fmt.Sprintf("%s (%d)", a.Name, a.Age)
}

type Animal struct {
	Name string
	Age  int
}

	a := Animal{
		Name: "string",
		Age:  5,
	}

	selfDefine := AnimalSelfDefine{
		Name: "string",
		Age:  5,
	}

	fmt.Printf("%s\n", a)          //{string %!s(int=5)}
	fmt.Printf("%s\n", selfDefine) //string (5)

	fmt.Printf("%q\n", a)          // {"string" '\x05'}
	fmt.Printf("%q\n", selfDefine) //"string (5)"

	fmt.Printf("%v\n", a)          // {string 5}
	fmt.Printf("%v\n", selfDefine) // string (5)

	fmt.Printf("%x\n", a)          // {737472696e67 5}
	fmt.Printf("%x\n", selfDefine) //737472696e6720283529  (等同 fmt.Printf("%x\n", "string (5)"))

	fmt.Printf("%X\n", a)          //  {737472696E67 5}
	fmt.Printf("%X\n", selfDefine) // 737472696E6720283529 (等同 fmt.Printf("%X\n", "string (5)"))

看上面的測試輸出,也可以發現 未實現string()方法的結構體, 在格式輸出時,相當於把結構體的每個成員分別格式化,用空格拼接。

其實GO語言內部,複合類型的操作數,如切片和結構體,格式化動作verb遞歸地應用於其每一個成員,而不是作爲整體一個操作數使用。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章