1. Số thực dấu phẩy động (Floating-point)
Tổng quan
- Kiểu số thực được dùng để lưu trữ các giá trị có phần thập phân.
- Có thể gán một số nguyên cho biến kiểu số thực, nhưng không thể gán ngược lại.
- Kết quả của phép toán trên số thực luôn là số thực.
- Go cung cấp hai loại:
float32vàfloat64.
Phạm vi giá trị
| Kiểu | Giá trị tối đa |
|---|---|
| float32 | 3.40e+38 |
| float64 | 1.798e+308 |
Để lấy nhanh các giá trị này, có thể sử dụng hằng số trong gói math:
package main
import (
"fmt"
"math"
)
func main() {
fmt.Println(math.MaxFloat32)
fmt.Println(math.MaxFloat64)
}
Phép toán trên số thực
float32vàfloat64không thể tính trực tiếp với nhau, cần ép kiểu.
package main
import "fmt"
func main() {
var x float32 = 2.5
var y float64 = 4.1
fmt.Println(x + float32(y))
fmt.Println(float64(x) + y)
}
- Nên ưu tiên dùng
float64vì tuy tốn bộ nhớ hơn, nhưngfloat32dễ gây sai số khi tính toán nhiều. - Phép toán giữa hai số nguyên cho kết quả là số nguyên, giữa hai số thực cho kết quả là số thực.
package main
import "fmt"
func main() {
var m, n int = 5, 2
var p, q float64 = 7, 3
fmt.Println(m / n)
fmt.Println(p / q)
}
2. Kiểu Boolean
Giới thiệu
- Từ khóa:
bool. - Chỉ có hai giá trị:
true(đúng, tương ứng với 1 trong nhị phân) vàfalse(sai, tương ứng với 0). - Không thể ép kiểu giữa
boolvà các kiểu khác. - Kích thước: 1 byte.
- Thường dùng trong các câu lệnh điều kiện.
Ví dụ
Khai báo biến bool:
package main
import "fmt"
func main() {
var flag1 bool = true
var flag2 bool = false
var flag3 = true
flag4 := false
fmt.Println(flag1, flag2, flag3, flag4)
}
Sử dụng unsafe.Sizeof() để kiểm tra kích thước:
package main
import (
"fmt"
"unsafe"
)
func main() {
val := false
fmt.Println(unsafe.Sizeof(val))
}
Mặc dù bool chiếm 1 byte, nhưng không thể ép kiểu sang int8 hay byte:
package main
import "fmt"
func main() {
var a int8 = 1
var b byte = 0
var c bool = false
fmt.Println(a, b, c)
// Các dòng sau sẽ báo lỗi
// a = int8(c)
// b = byte(c)
// c = bool(a)
// c = bool(b)
b = byte(a) // Hợp lệ
}
Biến bool có thể nhận giá trị từ biểu thức so sánh hoặc logic.
3. Toán tử
Tổng quan
Go hỗ trợ nhiều loại toán tử: số học, so sánh, logic, gán, quan hệ, bit. Cần chú ý thứ tự ưu tiên khi kết hợp.
Toán tử số học
| Toán tử | Ý nghĩa |
|---|---|
| + | Cộng |
| - | Trừ |
| * | Nhân |
| / | Chia |
| % | Chia lấy dư |
| ++ | Tăng 1 |
| -- | Giảm 1 |
Toán tử so sánh
| Toán tử | Ý nghĩa |
|---|---|
| == | Bằng nhau |
| != | Khác nhau |
| > | Lớn hơn |
| < | Nhỏ hơn |
| >= | Lớn hơn hoặc bằng |
| <= | Nhỏ hơn hoặc bằng |
Toán tử logic
| Toán tử | Ý nghĩa |
|---|---|
| ! | Phủ định |
| && | Và (cả hai đều đúng) |
| || | Hoặc (một trong hai đúng) |
Toán tử gán
| Toán tử | Ý nghĩa |
|---|---|
| = | Gán giá trị |
| += | Cộng và gán |
| -= | Trừ và gán |
| *= | Nhân và gán |
| /= | Chia và gán |
| %= | Chia lấy dư và gán |
| <<= | Dịch trái và gán |
| >>= | Dịch phải và gán |
| &= | AND bit và gán |
| |= | OR bit và gán |
| ^= | XOR bit và gán |
4. Toán tử bit
Khái niệm cơ bản: Mã nguồn, mã đảo, mã bù
- Với số dương, cả ba loại mã đều giống giá trị nhị phân gốc.
- Với số âm:
- Mã nguồn: biểu diễn nhị phân của giá trị tuyệt đối.
- Mã đảo: đảo tất cả các bit của mã nguồn.
- Mã bù: mã đảo cộng thêm 1. Đây là cách máy tính lưu trữ số âm.
Toán tử bit trong Go
| Toán tử | Ý nghĩa |
|---|---|
| << | Dịch trái |
| >> | Dịch phải |
| | | OR: bit nào là 1 thì kết quả là 1 |
| & | AND: cả hai đều là 1 mới cho kết quả 1 |
| ^ | XOR: giống nhau là 0, khác nhau là 1 |
| &^ | AND NOT: nếu bit bên phải là 0 thì giữ nguyên bên trái, nếu là 1 thì xóa về 0 |
5. Chuỗi (String)
Tổng quan
- Chuỗi là một dãy ký tự bất biến. Có thể chứa chữ, số, ký tự đặc biệt, nhưng chuỗi số không thể dùng trong phép tính toán.
- Từ khóa:
string.
var msg string = "hello"
name := "world"
- Giá trị chuỗi được đặt trong dấu ngoặc kép
"". Nếu dùng dấu backtick``, nội dung sẽ được giữ nguyên định dạng (kể cả ký tự đặc biệt).
a := "line1\nline2"
b := `line1\nline2`
fmt.Println(a) // In: line1 (xuống dòng) line2
fmt.Println(b) // In: line1\nline2
Chuyển đổi giữa chuỗi và số
Gói strconv cung cấp các hàm hỗ trợ chuyển đổi.
Chuỗi sang số nguyên
package main
import (
"fmt"
"strconv"
)
func main() {
s := "42"
// ParseInt(chuỗi, cơ số, kích thước bit)
i, _ := strconv.ParseInt(s, 10, 64)
fmt.Println(i)
fmt.Printf("%T\n", i)
// Cách viết ngắn gọn: Atoi (tương đương ParseInt với cơ số 10 và kích thước 64)
j, _ := strconv.Atoi(s)
fmt.Println(j)
}
Số nguyên sang chuỗi
package main
import (
"fmt"
"strconv"
)
func main() {
num := 42
// FormatInt(số int64, cơ số)
s := strconv.FormatInt(int64(num), 10)
fmt.Println(s)
fmt.Printf("%T\n", s)
// Cách thông dụng: Itoa (tương đương FormatInt với cơ số 10)
s2 := strconv.Itoa(num)
fmt.Println(s2)
}
Chuỗi sang số thực
package main
import (
"fmt"
"strconv"
)
func main() {
s := "3.14"
// ParseFloat(chuỗi, bitSize: 32 hoặc 64)
f, _ := strconv.ParseFloat(s, 64)
fmt.Println(f)
fmt.Printf("%T\n", f)
}
Số thực sang chuỗi
package main
import (
"fmt"
"strconv"
)
func main() {
val := 2.718
// FormatFloat(số, định dạng, độ chính xác, bitSize)
result := strconv.FormatFloat(val, 'f', 3, 64)
fmt.Println(result)
fmt.Printf("%T\n", result)
}