Статья впервые опубликована из паблика: Время программирования Go
«Время программирования на Go», колонка, которая может привести вас к изучению языка Go. В то же время вы можете поискать в моем публичном аккаунте с тем же именем [Время программирования на Go] (макет красивый и больше подходит для чтения ), и вы сможете получить галантерею языка Go как можно скорее.
Руководство по серии
1. Одна статья по созданию среды разработки языка Go
2. Пять способов создания переменных в языке Go
1. Целое число
В языке Go целочисленный тип можно разделить на типы 10. Для удобства всеобщего изучения я организую эти типы в таблицу.
Разница между int и uint в том, чтоu
,имеютu
Описание не подписано, нетu
Представляет символ.
Объясните отличие этого символа
кint8
а такжеuint8
Например, 8 представляет 8 бит, а количество значений, которые можно представить, равно 2^8 = 256.
uint8 не имеет знака и может представлять все положительные числа, от 0 до 255, ровно 256 чисел.
int8 знаковый и может быть как положительным, так и отрицательным, что делать? Пополам -128-127, то есть ровно 256 чисел.
Int8 int16 int32 int64 Эти типы имеют значение в конце, которое указывает, что количество значений, которые они могут представлять, фиксировано.
И int не указывает количество цифр, указывая на то, что его размер может быть изменен, так что же это за изменение?
- Когда вы находитесь в 32-битной системе, int и uint занимают 4 байта, что составляет 32 бита.
- Если вы работаете в 64-битной системе, и int, и uint занимают 8 байтов, то есть 64 бита.
По этой причине вам следует избегать использования int и uint и использовать более точные int32 и int64 в некоторых сценариях, таких как двоичные передачи, чтение и запись описаний файловой структуры (чтобы предотвратить влияние на файловую структуру различных компиляций). Влияние длины байта целевой платформы)
Представление разных баз
По привычке при инициализации переменных типа данных integer мы будем использовать десятичную запись, поскольку она наиболее интуитивно понятна, например, представляет целое число 10.
var num int = 10
Однако вы должны понимать, что вы можете использовать и другие системы счисления для представления целых чисел, например, наиболее часто используемые двоичные, восьмеричные и шестнадцатеричные.
Бинарный: с0b
или0B
префикс
var num01 int = 0b1100
шестнадцатеричный: с0o
или0O
префикс
var num02 int = 0o14
Шестнадцатеричный: с0x
префикс
var num03 int = 0xC
В следующем коде для представления десятичных значений используются двоичные, восьмеричные и шестнадцатеричные числа: 12
package main
import (
"fmt"
)
func main() {
var num01 int = 0b1100
var num02 int = 0o14
var num03 int = 0xC
fmt.Printf("2进制数 %b 表示的是: %d \n", num01, num01)
fmt.Printf("8进制数 %o 表示的是: %d \n", num02, num02)
fmt.Printf("16进制数 %X 表示的是: %d \n", num03, num03)
}
Вывод выглядит следующим образом
2进制数 1100 表示的是: 12
8进制数 14 表示的是: 12
16进制数 C 表示的是: 12
В приведенном выше коде используется функция форматирования пакета fmt, вы можете обратиться сюда, чтобы увидеть приведенный выше код.
%b 表示为二进制
%c 该值对应的unicode码值
%d 表示为十进制
%o 表示为八进制
%q 该值对应的单引号括起来的go语法字符字面值,必要时会采用安全的转义表示
%x 表示为十六进制,使用a-f
%X 表示为十六进制,使用A-F
%U 表示为Unicode格式:U+1234,等价于"U+%04X"
%E 用科学计数法表示
%f 用浮点数表示
2. Плавающая точка
Значение типа с плавающей запятой обычно состоит из целой части, десятичной точки..
" и дробная часть.
Среди них целая часть и дробная часть представлены десятичной записью. Но есть и другой способ выразить это. Это добавление экспоненциальной части к нему. Показатель степени состоит из «E» или «e» и десятичного числа со знаком. Например,3.7E-2
Представляет число с плавающей запятой0.037
. Другой пример:3.7E+1
Представляет число с плавающей запятой37
.
Иногда также можно упростить представление значений типа с плавающей запятой. Например,37.0
можно упростить до37
. Другой пример:0.037
можно упростить до.037
.
Следует отметить, что в Go соответствующая часть числа с плавающей запятой может быть представлена только десятичной записью, а не восьмеричной или шестнадцатеричной записью. Например,03.7
Должен представлять число с плавающей запятой3.7
.
поплавок32 и поплавок64
Язык Go предоставляет два точных числа с плавающей запятой float32 и float64.
float32, что является одинарной точностью, о которой мы часто говорим, память занимает 4 байта, то есть 4 * 8 = 32 бита, из которых 1 бит используется для знака, 8 бит используются для экспоненты, а остальные 23 бита представляют мантисса
float64, то есть знакомая нам двойная точность, память занимает 8 байт, то есть 8*8=64 бита, из которых 1 бит используется для знака, 11 бит – для экспоненты, а остальные 52 биты представляют мантиссу
Так что же означает точность? Сколько значащих битов?
Точность в основном зависит от количества цифр в мантиссе.
Для float32 (одинарная точность) мантисса составляет 23 бита.За исключением всех 0, минимум равен 2^-23, что приблизительно равно 1,19*10^-7, поэтому дробная часть числа с плавающей запятой может быть точной только до следующие 6 цифр плюс одна цифра перед запятой, то есть 7 значащих цифр.
Точно так же часть мантиссы числа float64 (одинарная точность) составляет 52 бита, минимальное значение равно 2^-52, что составляет примерно 2,22*10^-16, поэтому точность составляет 15 знаков после запятой плюс один разряд перед запятой. десятичная точка, эффективное количество цифр составляет 16 бит.
Из вышеизложенного можно сделать следующие выводы:
1. Есть много значений, которые могут представлять float32 и float64
Типы с плавающей запятой могут варьироваться от очень маленьких до очень больших. Границы диапазона значений с плавающей запятой можно найти в пакете math:
- Константа math.MaxFloat32 представляет максимальное значение, которое может принимать float32, что составляет около 3,4e38;
- Константа math.MaxFloat64 представляет максимальное значение, которое может принимать float64, что составляет около 1,8e308;
- Наименьшие значения, которые могут представлять float32 и float64, составляют 1,4e-45 и 4,9e-324 соответственно.
Во-вторых, значение велико, но точность ограничена.
Хотя люди могут представлять большое количество значений, но биты точности не так велики.
- Точность float32 может обеспечить только около 6 знаков после запятой (после представления постнаучной записи, 6 знаков после запятой)
- Точность float64 обеспечивает точность около 15 знаков после запятой (15 знаков после запятой после представления постнаучных обозначений).
При чем тут точность?
Например, если число 10000018 представлено типом float32, поскольку его значащие цифры составляют 7 цифр, 10000018 выражается в экспоненциальном представлении, то есть 1,0000018 * 10^7, что может быть с точностью до 6 знаков после запятой.
В настоящее время, после использования экспоненциальной записи, после запятой 7 цифр, что как раз соответствует нашим требованиям к точности Что это значит? На этом этапе вы можете выполнять математические операции, такие как +1 или -1 с этим числом, чтобы гарантировать точность результата расчета.
import "fmt"
var myfloat float32 = 10000018
func main() {
fmt.Println("myfloat: ", myfloat)
fmt.Println("myfloat: ", myfloat+1)
}
Вывод выглядит следующим образом
myfloat: 1.0000018e+07
myfloat: 1.0000019e+07
Критический случай данных, которые просто соответствуют требованиям точности, указан выше.Для сравнения ниже приведен пример, который просто не соответствует требованиям точности. Просто добавьте еще одну цифру к этому значению.
Измените его на 100000187, также используйте тип float32 и представьте его в экспоненциальном представлении.Из-за ограниченной точности 7 цифр после запятой являются точными, но если вы выполняете над ним математические операции, поскольку восьмая цифра не может быть представлена, так седьмой после операции значение бита становится неточным.
Здесь мы пишем код для проверки, согласно нашему пониманию ниже myfloat01 = 100000182 , для+5
После операции он должен быть равен myfloat02=100000187,
import "fmt"
var myfloat01 float32 = 100000182
var myfloat02 float32 = 100000187
func main() {
fmt.Println("myfloat: ", myfloat01)
fmt.Println("myfloat: ", myfloat01+5)
fmt.Println(myfloat02 == myfloat01+5)
}
Однако, поскольку его тип — float32, а точность недостаточна, результат окончательного сравнения неравный (неточный с седьмого знака после запятой).
myfloat: 1.00000184e+08
myfloat: 1.0000019e+08
false
Из-за проблемы точности происходит это очень странное явление,myfloat == myfloat +1
вернусьtrue
.