Regular Expressions in Go with Examples
Regular expressions (regex) are a powerful tool for searching, extracting, and replacing text based on patterns. In the Go language (Golang), working with regular expressions is implemented through the standard regexp package. In this article, we will thoroughly explore how to use regular expressions in Go: from simple searching to complex replacements with capture groups.
1. Basics of the regexp Package
The regexp package provides two main approaches: quick one-time use (package-level functions) and high-performance work with a precompiled pattern (the Regexp struct). For repeated use, always compile the pattern in advance.
Compiling a Regular Expression
package main
import ( "fmt" "regexp")
func main() { // Compiling a pattern (recommended method with error handling) pattern, err := regexp.Compile(`\\d+`) if err != nil { fmt.Println("Compilation error:", err) return } // For simple cases — without error handling (panics on invalid pattern) patternMust := regexp.MustCompile(`[a-z]+`) fmt.Println(pattern, patternMust)}Compile returns an error if the pattern is invalid. MustCompile panics — use it only for static patterns.
2. Basic Operations: Searching and Matching
Let's look at the main methods for checking matches and searching substrings.
Checking for a Partial Match
pattern := regexp.MustCompile(`go`)text := "I am studying Golang"
// MatchString — does the string contain a substring matching the patternmatched := pattern.MatchString(text)fmt.Println(matched) // true (because "go" is contained in "Golang")Checking for a Full Match
// To check that the entire string matches the pattern, use anchors ^ and $fullPattern := regexp.MustCompile(`^[a-zA-Z]+$`)fmt.Println(fullPattern.MatchString("Hello")) // truefmt.Println(fullPattern.MatchString("Hello1")) // falseFinding the First Match
datePattern := regexp.MustCompile(`\\d{2}\\.\\d{2}\\.\\d{4}`)text := "Today is 15.03.2024, and tomorrow is 16.03.2024"
// FindString — returns the first matchfirstDate := datePattern.FindString(text)fmt.Println(firstDate) // "15.03.2024"Finding All Matches
// FindAllString — returns a slice of all matchesallDates := datePattern.FindAllString(text, -1) // -1 — all matchesfmt.Println(allDates) // ["15.03.2024" "16.03.2024"]
// Limiting the count: FindAllString(text, 1) — only the first one3. Capture Groups and Substitutions
Capture groups allow you to extract parts of a match. In Go, groups are denoted by parentheses ().
Extracting Data by Groups
// Pattern for extracting name and age: "Name: [name], Age: [number]"personPattern := regexp.MustCompile(`Name: (\\w+), Age: (\\d+)`)text := "Name: Alexey, Age: 30"
// FindStringSubmatch — returns a slice: [full_match, group1, group2, ...]matches := personPattern.FindStringSubmatch(text)if len(matches) > 0 { fmt.Println("Full match:", matches[0]) // "Name: Alexey, Age: 30" fmt.Println("Name:", matches[1]) // "Alexey" fmt.Println("Age:", matches[2]) // "30"}Named Groups (Go 1.21+)
// Since Go version 1.21, you can use named groups: (?P<name>pattern)pattern := regexp.MustCompile(`(?P<name>\\w+)@(?P<domain>\\w+\\.\\w+)`)text := "test@example.com"
// SubexpNames — get the group namesgroupNames := pattern.SubexpNames()matches := pattern.FindStringSubmatch(text)
// Create a map: group_name