英文:
What is the difference between the string and []byte in Go?
问题
s := "some string"
b := []byte(s) // 将字符串转换为字节切片
s2 := string(b) // 将字节切片转换为字符串
在Go语言中,string
和[]byte
有什么区别?
何时使用"he"或"she"?
为什么?
bb := []byte{'h','e','l','l','o',127}
ss := string(bb)
fmt.Println(ss)
hello
输出结果只是"hello",缺少了127,有时我觉得这很奇怪。
英文:
s := "some string"
b := []byte(s) // convert string -> []byte
s2 := string(b) // convert []byte -> string
what is the difference between the string
and []byte
in Go?
When to use "he" or "she"?
Why?
bb := []byte{'h','e','l','l','o',127}
ss := string(bb)
fmt.Println(ss)
> hello
The output is just "hello"
, and lack of 127
, sometimes I feel that it's weird.
答案1
得分: 20
string
和[]byte
是不同的类型,但它们可以相互转换:
- 将
[]byte
转换为string
类型会生成一个字符串,其中连续的字节是切片的元素。 - 将
string
类型的值转换为[]byte
类型会生成一个切片,其中连续的元素是字符串的字节。
在Go语言中,字符串实际上非常简单:它们只是带有一些额外语法支持的只读字节切片。
使用哪个取决于你的需求。字符串是不可变的,因此它们可以共享,并且你可以确保它们不会被修改。
字节切片可以被修改(即可以修改其背后的数组内容)。
如果你需要频繁地将string
转换为[]byte
(例如,因为你需要将其写入io.Writer()
),你应该考虑一开始就将其存储为[]byte
。
还要注意,你可以有string
常量,但没有切片常量。这可能是一个小的优化。此外要注意:
- 如果
s
是一个字符串常量,表达式len(s)
是常量。
此外,如果你正在使用已经编写好的代码(无论是标准库、第三方包还是你自己的代码),在大多数情况下,都会明确给出你需要传递的参数和值,或者返回的值。例如,如果你从io.Reader
中读取数据,你需要一个[]byte
来接收读取的字节,而不能使用string
。
在这个例子中:
bb := []byte{'h','e','l','l','o',127}
这里发生的是你使用了一个复合字面量(切片字面量)来创建和初始化一个新的[]byte
类型的切片(使用了短变量声明)。你指定了常量来列出切片的初始元素。你还使用了一个字节值127
,这取决于平台/控制台,可能有或可能没有可视化表示。
英文:
string
and []byte
are different types, but they can be converted to one another:
> 3 . Converting a slice of bytes to a string type yields a string whose successive bytes are the elements of the slice.
>
> 4 . Converting a value of a string type to a slice of bytes type yields a slice whose successive elements are the bytes of the string.
Blog: Arrays, slices (and strings): The mechanics of 'append':
> Strings are actually very simple: they are just read-only slices of bytes with a bit of extra syntactic support from the language.
Also read: Strings, bytes, runes and characters in Go
When to use one over the other?
Depends on what you need. Strings are immutable, so they can be shared and you have guarantee they won't get modified.
Byte slices can be modified (meaning the content of the backing array).
Also if you need to frequently convert a string
to a []byte
(e.g. because you need to write it into an io.Writer()
), you should consider storing it as a []byte
in the first place.
Also note that you can have string
constants but there are no slice constants. This may be a small optimization. Also note that:
> The expression len(s)
is constant if s
is a string constant.
Also if you are using code already written (either standard library, 3rd party packages or your own), in most of the cases it is given what parameters and values you have to pass or are returned. E.g. if you read data from an io.Reader
, you need to have a []byte
which you have to pass to receive the read bytes, you can't use a string
for that.
This example:
bb := []byte{'h','e','l','l','o',127}
What happens here is that you used a composite literal (slice literal) to create and initialize a new slice of type []byte
(using Short variable declaration). You specified constants to list the initial elements of the slice. You also used a byte value 127
which - depending on the platform / console - may or may not have a visual representation.
答案2
得分: 4
晚了一点,但希望这可以帮到你。
简单来说
- 位(Bit):机器用
0
和1
来表示所有的信息。 - 字节(Byte):由
8个位(bit)
组成,表示UTF-8编码,即字符。 - type:给定数据类型的切片。切片是动态大小的数组。
- byte:这是一个字节切片,即一个
动态
大小的数组,其中包含字节,即每个元素是一个UTF-8字符。 - 字符串(String):字节的只读切片,即
不可变
的。
有了这些基础知识:
s := "Go"
bs := []byte(s)
fmt.Printf("%s", bs) // 输出:Go
fmt.Printf("%d", bs) // 输出:[71 111]
或者
bs := []byte{71, 111}
fmt.Printf("%s", bs) // 输出:Go
%s
将字节切片转换为字符串
%d
获取字节的UTF-8十进制值
重要提示:
由于字符串是不可变的
,它们不能在内存中更改。每次你向字符串添加或删除内容时,Go都会在内存中创建一个新的字符串。另一方面,字节切片是可变的
,所以当你更新一个字节切片时,你不会在内存中重新创建新的内容。
因此,在选择合适的数据结构时,可能会对你的应用程序性能产生影响。
英文:
Late but i hope this could help.
In simple words
- Bit:
0
and1
is how machines represents all the information - Byte:
8 bits
that represents UTF-8 encodings i.e. characters - type: slice of a given data type. Slices are dynamic size arrays.
- byte: this is a byte slice i.e. a
dynamic
size array that contains bytes i.e. each element is a UTF-8 character. - String: read-only slices of bytes i.e.
immutable
With all this in mind:
s := "Go"
bs := []byte(s)
fmt.Printf("%s", bs) // Output: Go
fmt.Printf("%d", bs) // Output: [71 111]
or
bs := []byte{71, 111}
fmt.Printf("%s", bs) // Output: Go
%s
converts byte slice to string
%d
gets UTF-8 decimal value of bytes
IMPORTANT:
As strings are immutable
, they cannot be changed within memory, each time you add or remove something from a string, GO creates a new string in memory. On the other hand, byte slices are mutable
so when you update a byte slice you are not recreating new stuffs in memory.
So choosing the right structure could make a difference in your app performance.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论