Go 语言核心语法结构与算法实现解析
循环控制与流程跳转
在掌握 Go 语言的基础控制流时,理解标准循环与非标准跳转的区别至关重要。以下演示如何通过两种不同的机制实现计数逻辑。
方案一:标准迭代模式
这是 Go 推荐的标准写法,使用 for 语句进行固定次数的迭代。
package main
import "fmt"
func main() {
const totalIterations = 10
var currentIdx int
for currentIdx = 0; currentIdx < totalIterations; currentIdx++ {
fmt.Printf("Index: %d\n", currentIdx)
}
}方案二:条件跳转模式
虽然现代开发中极少使用 goto,但了解其标签定义与跳转逻辑有助于理解底层控制流。此例禁止使用关键字 for 来实现相同功能。
package main
import "fmt"
func main() {
counter := 0
START_LOOP:
if counter >= 10 {
return
}
fmt.Printf("Value at label: %d\n", counter)
counter++
goto START_LOOP
}
数据集合遍历与存储
在处理数组(Array)或切片(Slice)时,利用 range 关键字可以简化索引操作。
package main
import "fmt"
func main() {
// 初始化定长数组
dataSet := [10]int{}
// 填充数据
for idx := range dataSet {
dataSet[idx] = idx * 10
}
// 输出数据
fmt.Println("Traversing dataset:")
for _, val := range dataSet {
fmt.Printf("Item: %d\n", val)
}
}
经典算法:FizzBuzz
这是一个用于测试条件分支判断能力的经典问题。我们需要打印 1 到 100,但在特定倍数时输出对应文本。
package main
import "fmt"
func solveFizzBuzz(limit int) {
for n := 1; n <= limit; n++ {
isDivisibleByThree := n%3 == 0
isDivisibleByFive := n%5 == 0
output := ""
if isDivisibleByThree {
output += "Fizz"
}
if isDivisibleByFive {
output += "Buzz"
}
if output != "" {
fmt.Println(output)
} else {
fmt.Println(n)
}
}
}
func main() {
solveFizzBuzz(100)
}
嵌套循环与图形输出
利用嵌套循环可以构建复杂的字符矩阵。下面的示例生成一个由字母 'A' 构成的三角形图案。
package main
import "fmt"
func printPyramid(maxHeight int) {
for row := 1; row <= maxHeight; row++ {
line := ""
for col := 0; col < row; col++ {
line += "A"
}
fmt.Println(line)
}
}
func main() {
printPyramid(10)
}
字符串编码与统计
Go 中的字符串是只读的字节序列。要正确统计字符数量(特别是包含中文等多字节字符时),需要区分字节长度和 Rune(Unicode 码点)数量。
package main
import (
"fmt"
"unicode/utf8"
)
func analyzeString(target string) {
bytesLen := len([]byte(target))
runesCount := utf8.RuneCountInString(target)
fmt.Printf("原始内容:%s\n", target)
fmt.Printf("字节总数:%d\n", bytesLen)
fmt.Printf("字符总数 (Rune):%d\n", runesCount)
}
func main() {
inputText := "asSASA ddd dsjkdsjs dk 汉子"
analyzeString(inputText)
}
字符串替换操作
当需要对特定位置的子串进行修改时,可以使用 strings 包提供的工具函数,或者手动拼接切片。
package main
import (
"fmt"
"strings"
)
func modifySegment(original string, startIdx, length int, replacement string) string {
subStr := original[startIdx : startIdx+length]
return strings.Replace(original, subStr, replacement, 1)
}
func main() {
source := "asSASA ddd dsjkdsjs dk"
// 从索引 3 开始替换 3 个字符为 "abc"
result := modifySegment(source, 3, 3, "abc")
fmt.Printf("原串: %s\n修改后: %s\n", source, result)
}
字符串逆转处理
由于直接索引字符串可能会截断多字节字符,安全的方法是先将字符串转换为 Rune 切片进行逆序操作。
package main
import "fmt"
func reverseText(s string) string {
runes := []rune(s)
length := len(runes)
// 双指针交换法
for l, r := 0, length-1; l < r; l, r = l+1, r-1 {
runes[l], runes[r] = runes[r], runes[l]
}
return string(runes)
}
func main() {
textToReverse := "foobar中文测试"
fmt.Println("反转结果:", reverseText(textToReverse))
}
浮点数切片聚合
在实际业务中,经常需要计算数据集的统计值。这里封装了一个函数来计算 float64 类型切片的算术平均值。
package main
import "fmt"
func calculateMean(numbers []float64) float64 {
if len(numbers) == 0 {
return 0.0
}
sum := 0.0
for _, num := range numbers {
sum += num
}
return sum / float64(len(numbers))
}
func main() {
values := []float64{1.5, 2.3, 4.8, 9.2, 5.0}
meanVal := calculateMean(values)
fmt.Printf("数据集: %v\n", values)
fmt.Printf("平均值: %.2f\n", meanVal)
}