FindAllStringIndex (строка s, n int) возвращает байтовые индексы начала / конца (т. Е. Срезы) всех последовательных совпадений выражения:
package main
import "fmt"
import "io/ioutil"
import "regexp"
func main() {
fname := "C:\\Users\\UserName\\go\\src\\so56798431\\fname"
b, err := ioutil.ReadFile(fname)
if err != nil {
panic(err)
}
re, err := regexp.Compile("findme")
if err != nil {
// handle error
}
fmt.Println(re.FindAllStringIndex(string(b), -1))
}
Выход:
[[12 18] [32 38]]
Примечание: я сделал это в Microsoft Windows, но сохранил файл в формате UNIX (перевод строки); если входной файл сохранен в формате Windows (возврат каретки и перевод строки), смещение байтов увеличится до 13 и 35 соответственно.
ОБНОВЛЕНИЕ: для больших файлов используйте bufio.Scanner ; например:
package main
import (
"bufio"
"fmt"
"log"
"os"
"regexp"
)
func main() {
fname, err := os.Open("C:\\Users\\UserName\\go\\src\\so56798431\\fname")
if err != nil {
log.Fatal(err)
}
defer fname.Close()
re, err := regexp.Compile("findme")
if err != nil {
// handle error
}
scanner := bufio.NewScanner(fname)
bytesRead := 0
for scanner.Scan() {
b := scanner.Text()
//fmt.Println(b)
results := re.FindAllStringIndex(b, -1)
for _, result := range results {
fmt.Println(bytesRead + result[0])
}
// account for UNIX EOL marker
bytesRead += len(b) + 1
}
if err := scanner.Err(); err != nil {
log.Fatal(err)
}
}
Выход:
12
32