Maison > Article > développement back-end > Expression régulière avec golang pour correspondre aux lignes complètes contenant « erreur » ou « avertissement » (insensible à la casse)
L'éditeur PHP Baicao présente aujourd'hui comment utiliser des expressions régulières pour faire correspondre des lignes complètes contenant "erreur" ou "avertissement" (insensible à la casse) en golang. Les expressions régulières sont un puissant outil de correspondance de modèles de texte qui peut nous aider à trouver du contenu qui correspond à un modèle spécifique dans une chaîne. En Golang, l'utilisation d'expressions régulières nécessite l'introduction du package regexp et l'utilisation de la fonction Compile pour compiler l'expression régulière. Ensuite, nous présenterons en détail comment utiliser les expressions régulières pour la correspondance de lignes dans Golang.
Je souhaite imprimer la ligne complète de chaque ligne du fichier journal qui contient un avertissement ou une erreur (insensible à la casse) à l'utilisateur.
CONTENU QUE :
[01-17|18:53:38.179] info server/server.go:381 this would be skipped [01-17|18:53:38.280] info server/server.go:620 this also [01-17|18:53:41.180] warn server/server.go:388 something is warned, so show this [01-17|18:53:41.394] warn server/server.go:188 something reported an ->error<- [01-17|18:53:41.395] error server/server.go:191 blabla [01-17|18:53:41.395] debug server/server.go:196 obviously skipped [01-17|18:53:41.395] debug server/server.go:196 this debug contains an ->error<- so match this [01-17|18:53:41.395] warn server/server.go:198 you get the idea
Je veux :
[01-17|18:53:41.180] warn server/server.go:388 something is warned, so show this [01-17|18:53:41.394] warn server/server.go:188 something reported an ->error<- [01-17|18:53:41.395] error server/server.go:191 blabla [01-17|18:53:41.395] debug server/server.go:196 this debug contains an ->error<- so match this [01-17|18:53:41.395] warn server/server.go:198 you get the idea
J'ai commencé innocemment
errorregex := regexp.mustcompile(`(?is)error|warn`)
Il s'imprimera simplement (à partir d'une exécution différente, peut ne pas correspondre exactement à l'exemple ci-dessus)
warn error
Ensuite, j'ai pensé que je devrais le changer pour qu'il corresponde davantage :
errorRegEx := regexp.MustCompile(`(?is).*error.*|.*warn.*`)
Mais cela n’imprime rien du tout
Comment obtenir la ligne complète et toutes les lignes où l'avertissement ou l'erreur (insensible à la casse) correspondront ?
ps : Ce n'est pas la même chose que la ligne de correspondance d'expression régulière suggérée contenant une chaîne, car il s'agit d'une question spécifiquement pour le langage go
, qui ne semble pas utiliser exactement le même moteur standard.
Considérant que la question a été marquée comme dupe, le commentaire de l'op est le suivant.
Cette question est marquée comme un doublon, et le message lié contient de nombreuses réponses que nous pouvons utiliser pour essayer de rassembler une réponse à la question du PO, mais il n'est toujours pas complet car les réponses semblent être liées à pcre and go en utilisant re2.
var logs = ` [01-17|18:53:38.179] info server/server.go:381 this would be skipped [01-17|18:53:38.280] info server/server.go:620 this also [01-17|18:53:41.180] warn server/server.go:388 something is warned, so show this [01-17|18:53:41.394] warn server/server.go:188 something reported an ->error<- [01-17|18:53:41.395] error server/server.go:191 blabla [01-17|18:53:41.395] debug server/server.go:196 obviously skipped [01-17|18:53:41.395] debug server/server.go:196 this debug contains an ->error<- so match this [01-17|18:53:41.395] warn server/server.go:198 you get the idea ` func init() { logs = strings.trimspace(logs) }
Tout d'abord, je ne comprends pas pourquoi cela n'imprime rien pour l'opération :
Ensuite, j'ai pensé que je devrais le changer pour qu'il corresponde davantage :
errorregex := regexp.mustcompile(`(?is).*error.*|.*warn.*`)
Mais cela n’imprime rien du tout
Parce que tout doit être imprimé :
fmt.println("original regexp:") reoriginal := regexp.mustcompile(`(?is).*error.*|.*warn.*`) lines := reoriginal.findallstring(logs, -1) fmt.println("match\t\tentry") fmt.println("=====\t\t=====") for i, line := range lines { fmt.printf("%d\t\t%q\n", i+1, line) }
original regexp: match entry ===== ===== 1 "[01-17|18:53:38.179] info server/server.go:381 this would be skipped\n[01-17|18:53:38.280] info server/server.go:620 this also\n[01-17|18:53:41.180] warn server/server.go:388 something is warned, so show this\n[01-17|18:53:41.394] warn server/server.go:188 something reported an ->error<-\n[01-17|18:53:41.395] error server/server.go:191 blabla\n[01-17|18:53:41.395] debug server/server.go:196 obviously skipped\n[01-17|18:53:41.395] debug server/server.go:196 this debug contains an ->error<- so match this\n[01-17|18:53:41.395] warn server/server.go:198 you get the idea"
(?is)...
中的 s
标志表示将换行符与点匹配 (.
)^1,并且因为您的星星 (*
) est gourmand^2, si une "erreur" ou un "avertissement" est trouvé, ils correspondront à tout dans la chaîne entière.
La vraie solution est de ne pas faire correspondre les points - supprimez le drapeau s
et vous obtenez le résultat souhaité :
fmt.println("whole text:") rewholetext := regexp.mustcompile(`(?i).*error.*|.*warn.*`) lines = rewholetext.findallstring(logs, -1) fmt.println("match\t\tentry") fmt.println("=====\t\t=====") for i, line := range lines { fmt.printf("%d\t\t%q\n", i+1, line) }
whole text: match entry ===== ===== 1 "[01-17|18:53:41.180] warn server/server.go:388 something is warned, so show this" 2 "[01-17|18:53:41.394] warn server/server.go:188 something reported an ->error<-" 3 "[01-17|18:53:41.395] error server/server.go:191 blabla" 4 "[01-17|18:53:41.395] debug server/server.go:196 this debug contains an ->error<- so match this" 5 "[01-17|18:53:41.395] warn server/server.go:198 you get the idea"
Maintenant, nous faisons la correspondance entre "n" instances (lignes valides) car nous utilisons le formulaire all
, qui recherche uniquement les correspondances qui ne se chevauchent pas :
Vous pouvez resserrer légèrement cette expression régulière :
`(?i).*(?:error|warn).*` // "anything before either "error" or "warn" and anything after (for a line)"
est un (?:...)
groupe qui ne capture pas ^1 parce que vous ne semblez pas vous soucier des cas individuels d'"erreur" ou d'"avertissement" dans chaque match.
r := strings.newreader(logs) scanner := bufio.newscanner(r) fmt.println("line-by-line:") reline := regexp.mustcompile(`(?i)error|warn`) fmt.println("match\tline\tentry") fmt.println("=====\t====\t=====") var matchno, lineno, match = 1, 1, "" for scanner.scan() { line := scanner.text() match = reline.findstring(line) if match != "" { fmt.printf("%d\t%d\t%q\n", matchno, lineno, line) matchno++ } lineno++ }
Line-by-line: match line entry ===== ==== ===== 1 3 "[01-17|18:53:41.180] Warn server/server.go:388 Something is warned, so show this" 2 4 "[01-17|18:53:41.394] warn server/server.go:188 Something reported an ->error<-" 3 5 "[01-17|18:53:41.395] Error server/server.go:191 Blabla" 4 7 "[01-17|18:53:41.395] DEBUG server/server.go:196 This debug contains an ->error<- so match this" 5 8 "[01-17|18:53:41.395] WARN server/server.go:198 You get the idea"Les trois exemples sont situés dans
ce terrain de jeu.
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!