Saya memiliki string yang berisi integer (yang telah dibaca dari file).
Saya mencoba mengonversi string
menjadi int
penggunaan strconv.ParseInt()
. ParseInt
mengharuskan saya memberikan bitsize (ukuran bit 0, 8, 16, 32, dan 64 sesuai dengan int, int8, int16, int32, dan int64).
Integer yang dibaca dari file berukuran kecil (yaitu harus sesuai dengan int normal). Jika saya memberikan bitsize 0, bagaimanapun, saya mendapatkan hasil tipe int64
(mungkin karena saya menjalankan OS 64-bit).
Mengapa ini terjadi? Bagaimana cara mendapatkan int normal? (Jika seseorang mengetahui dengan cepat kapan dan mengapa saya harus menggunakan tipe int yang berbeda, itu akan luar biasa!)
Sunting: Saya dapat mengubah int64 menjadi int normal menggunakan int([i64_var])
. Tapi saya masih tidak mengerti mengapa ParseInt()
memberi saya int64 ketika saya meminta bitsize 0.
parseInt(s, 0, 0)
, yang seharusnya menyimpulkan base10 (karena string tidak memiliki awalan dasar). Namun, Atoi adalah singkatan dari pemanggilanparseInt
dengan basis 10. Mengapa parameter basis membuat perbedaan pada tipe yang dikembalikan?0
cara kode mencoba untuk mengetahuinya sendiri. Namun terkadang hal ini tidak memungkinkan.11
(desimal) vs11
(biner) mewakili nilai yang sepenuhnya berbeda.parseInt(s, 10, 0)
". Tapi mengapa Atoi kembaliint
saatparseInt
mengembalikan int64?Atoi
itu ditambahkan hanya untuk mengakomodasi orang-orang yang lebih akrab dengan C API:int atoi ( const char * str );
Jawaban:
func ParseInt(s string, base int, bitSize int) (i int64, err error)
ParseInt selalu kembali
int64
bitSize
mendefinisikan rentang nilai. Jika nilai yang sesuai dengan s tidak dapat diwakili oleh bilangan bulat bertanda tangan dari ukuran yang diberikan, err.Err = ErrRange.http://golang.org/pkg/strconv/#ParseInt
type int int
int adalah tipe integer bertanda yang berukuran setidaknya 32 bit. Ini adalah tipe yang berbeda, bagaimanapun, dan bukan alias untuk, katakanlah, int32.
http://golang.org/pkg/builtin/#int
Jadi
int
bisa lebih besar dari 32 bit di masa depan atau pada beberapa sistem sepertiint
di C.Saya kira pada beberapa sistem
int64
mungkin lebih cepat dariint32
karena sistem itu hanya bekerja dengan 64 bit integer.Berikut adalah contoh error when
bitSize
8http://play.golang.org/p/_osjMqL6Nj
package main import ( "fmt" "strconv" ) func main() { i, err := strconv.ParseInt("123456", 10, 8) fmt.Println(i, err) }
sumber
int64
forint
di GOARCH amd64 danint32
untuk GOARCHint
32-bit. Setidaknya dengan kompiler default, saya tidak yakin tentang gccgo. Jadi "int
bisa lebih besar dari 32 bit ..." bukan hanya spekulasi, itu sebenarnya lebih mungkin karena target kompilasi 64-bit umumnya dianggap sebagai cabang utama di Go.ParseInt
selalu mengembalikanint64
nilai. Tergantung padabitSize
, nilai ini akan masuk ke dalamint
,int8
,int16
,int32
, atauint64
. Jika nilai tidak dapat diwakili oleh bilangan bulat bertanda dari ukuran yang diberikan olehbitSize
, makaerr.Err = ErrRange
.int
adalah 32 atau 64 bit, tergantung pada implementasinya. Biasanya 32 bit untuk kompiler 32-bit dan 64 bit untuk kompiler 64-bit.Untuk mengetahui ukuran sebuah
int
atauuint
, gunakanstrconv.IntSize
.Sebagai contoh,
package main import ( "fmt" "runtime" "strconv" ) func main() { fmt.Println(runtime.Compiler, runtime.GOARCH, runtime.GOOS) fmt.Println(strconv.IntSize) }
Keluaran:
gc amd64 linux 64
sumber
strconv.ParseInt
dan teman-teman mengembalikan versi 64-bit untuk menjaga API tetap bersih dan sederhana. Jika tidak, seseorang harus membuat versi terpisah untuk setiap jenis pengembalian yang mungkin. Atau kembaliinterface{}
, yang kemudian harus melalui pernyataan tipe. Tidak ada satupun yang ideal.int64
dipilih, karena dapat menampung ukuran integer apa pun hingga, dan termasuk, 64-bit yang didukung. Ukuran bit yang Anda berikan ke fungsi tersebut, memastikan bahwa nilainya dijepit dengan benar ke kisaran yang benar. Jadi, Anda cukup melakukan konversi jenis pada nilai yang dikembalikan, untuk mengubahnya menjadi jenis bilangan bulat apa pun yang Anda butuhkan.Adapun perbedaan antara
int
danint64
, ini bergantung pada arsitektur.int
hanyalah sebuah alias untuk integer 32-bit atau 64-bit, tergantung pada arsitektur yang Anda kompilasi.Untuk mata yang tajam: Nilai yang dikembalikan adalah bilangan bulat bertanda. Ada
strconv.ParseUint
fungsi terpisah untuk unsigned integer, yang mengembalikanuint64
dan mengikuti alasan yang sama seperti yang dijelaskan di atas.sumber
int
hanya sebuah alias - ini sebenarnya tipe yang berbeda. golang.org/pkg/builtin/#inttype int int32
harus diperlakukan sebagai tipe yang unik dan terpisah. Terutama karena memungkinkan fungsionalitas baru untuk didefinisikan untukint
jenis melalui penerapan metode baru.Untuk tujuan Anda,
strconv.Atoi()
akan lebih nyaman menurut saya.Jawaban lain sudah cukup lengkap tentang menjelaskan
int
jenisnya, tetapi saya pikir tautan ke spesifikasi bahasa Go bermanfaat di sini: http://golang.org/ref/spec#Numeric_typessumber
Dalam Go lang, setiap tipe dianggap sebagai tipe data terpisah yang tidak dapat digunakan secara bergantian dengan tipe dasar. Sebagai contoh,
type CustomInt64 int64
Dalam pernyataan di atas, CustomInt64 dan int64 built-in adalah dua tipe data yang terpisah dan tidak dapat digunakan secara bergantian.
Sama halnya dengan int, int32, dan int64, semuanya adalah tipe data terpisah yang tidak dapat digunakan secara bergantian. Di mana int32 adalah 32 tipe integernya, int64 adalah 64 bit dan ukuran tipe int generik bergantung pada platform. Lebar 32 bit pada sistem 32-bit dan lebar 64-bit pada sistem 64-bit. Jadi kita harus berhati-hati dan spesifik saat menentukan tipe data generik seperti int, uint, dan float. Ini dapat menyebabkan masalah di suatu tempat dalam kode dan akan merusak aplikasi di platform yang berbeda.
sumber