2013-03-14 67 views
9

我有一個包含我想從標準輸入fmt.Scanln讀3號線(),但一片這段代碼將無法正常工作:如何使fmt.Scanln()讀入整數

X := make([]int, 3) 
fmt.Scanln(X...) 
fmt.Printf("%v\n", X) 

我收到此錯誤信息:

cannot use X (type []int) as type []interface {} in function argument 

我不明白這一點。

回答

4

例如,

package main 

import "fmt" 

func intScanln(n int) ([]int, error) { 
    x := make([]int, n) 
    y := make([]interface{}, len(x)) 
    for i := range x { 
     y[i] = &x[i] 
    } 
    n, err := fmt.Scanln(y...) 
    x = x[:n] 
    return x, err 
} 

func main() { 
    x, err := intScanln(3) 
    if err != nil { 
     fmt.Println(err) 
     return 
    } 
    fmt.Printf("%v\n", x) 
} 

輸入:

1 2 3 

輸出:

[1 2 3] 
+0

爲什麼這不會導致輸出'[3,3,3]'? ''''''''''''''''''''可以用'0'初始化,當我在'main'函數中測試時,''全部指向相同的地址。 – dskinner 2013-03-14 18:06:10

+0

我看到'&x [i]'的地址是唯一的,但如果用'for i,v:= range x {...}來迭代,'v'的地址不是唯一的。 – dskinner 2013-03-14 18:19:26

+0

如果代替3的長度,我的輸入是不是靜態的?即有時'''[1]'''有時'''[1,2,3,4,5]''' – javidazac 2017-03-31 16:49:42

0

我認爲正確的版本應該是

X := make([]int, 3) 
fmt.Scanln(&X[0], &X[1], &X[2]) 
fmt.Printf("%v\n", X) 
+3

其實我有一堆線來處理,他們不是所有長度都一樣,有的有幾百個數字。 – Frolik 2013-03-14 16:33:05

1

此錯誤消息出現B/C有到[]int轉換爲[]interface{}沒有合理的方式。請注意,這是參照切片。所以您使用的語法是正確的,但fmt.Scanln預計[]interface{}。這在pkg fmt之外有影響。

我之所以看到這個原因是因爲Go允許您控制內存佈局,所以它目前沒有合理的方式來執行片轉換。這意味着在將它傳遞給期望給定類型的切片的函數之前,您需要手動進行轉換。例如:

package main 

import (
    "fmt" 
) 

func main() { 
    x := make([]int, 3) 
    y := make([]interface{}, 3) 
    y[0] = x[0] 
    y[1] = x[1] 
    y[2] = x[2] 

    fmt.Println(y...) 
} 

或者一些更普遍:

x := make([]int, 3) 
    y := make([]interface{}, len(x)) 
    for i, v := range x { 
     y[i] = v 
    } 

    fmt.Println(y...) 

關於你提到的具體問題,請參閱以下內容:

x := make([]*int, 3) 
    for i := range x { 
     x[i] = new(int) 
    } 

    y := make([]interface{}, 3) 

    for i, v := range x { 
     y[i] = v 
    } 

    if _, err := fmt.Scanln(y...); err != nil { 
     fmt.Println("Scanln err: ", err) 
    } 

    for _, v := range y { 
     val := v.(*int) 
     fmt.Println(*val) 
    } 
+0

謝謝,我不再接受錯誤,但是當我打印時,我得到了零,我想是因爲fmt.Scanln()期望引用。我試過fmt.Scanln(&y ...),無濟於事。任何想法? – Frolik 2013-03-14 17:18:22

+0

我更新了一個例子 – dskinner 2013-03-14 18:02:23

10

慣用圍棋將是:

func read(n int) ([]int, error) { 
    in := make([]int, n) 
    for i := range in { 
    _, err := fmt.Scan(&in[i]) 
    if err != nil { 
     return in[:i], err 
    } 
    } 
    return in, nil 
} 

interface{}意味着什麼。如果你不需要,請不要使用它。