Respostas:
Você deve poder usar quantificadores não gananciosos, especificamente * ?. Você provavelmente vai querer o seguinte:
Pattern MY_PATTERN = Pattern.compile("\\[(.*?)\\]");
Isso fornecerá um padrão que corresponderá à sua string e colocará o texto entre colchetes no primeiro grupo. Consulte a documentação da API de padrões para obter mais informações.
Para extrair a string, você pode usar algo como o seguinte:
Matcher m = MY_PATTERN.matcher("FOO[BAR]");
while (m.find()) {
String s = m.group(1);
// s now contains "BAR"
}
da maneira não regex:
String input = "FOO[BAR]", extracted;
extracted = input.substring(input.indexOf("["),input.indexOf("]"));
alternativamente, para um desempenho / uso de memória um pouco melhor (graças ao Hosam):
String input = "FOO[BAR]", extracted;
extracted = input.substring(input.indexOf('['),input.lastIndexOf(']'));
lastIndexOf(']')
vez disso, eu usaria , que manipularia colchetes aninhados. Além disso, acredito que usar o indexOf(char)
seria mais rápido que indexOf(String)
.
lastIndexOf
certamente será mais rápido encontrar o colchete.
Este é um exemplo de trabalho:
RegexpExample.java
package org.regexp.replace;
import java.util.ArrayList;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class RegexpExample
{
public static void main(String[] args)
{
String string = "var1[value1], var2[value2], var3[value3]";
Pattern pattern = Pattern.compile("(\\[)(.*?)(\\])");
Matcher matcher = pattern.matcher(string);
List<String> listMatches = new ArrayList<String>();
while(matcher.find())
{
listMatches.add(matcher.group(2));
}
for(String s : listMatches)
{
System.out.println(s);
}
}
}
Exibe:
value1
value2
value3
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public static String get_match(String s, String p) {
// returns first match of p in s for first group in regular expression
Matcher m = Pattern.compile(p).matcher(s);
return m.find() ? m.group(1) : "";
}
get_match("FOO[BAR]", "\\[(.*?)\\]") // returns "BAR"
public static List<String> get_matches(String s, String p) {
// returns all matches of p in s for first group in regular expression
List<String> matches = new ArrayList<String>();
Matcher m = Pattern.compile(p).matcher(s);
while(m.find()) {
matches.add(m.group(1));
}
return matches;
}
get_matches("FOO[BAR] FOO[CAT]", "\\[(.*?)\\]")) // returns [BAR, CAT]
Se você simplesmente precisar obter o que estiver entre []
, poderá usar o \[([^\]]*)\]
seguinte:
Pattern regex = Pattern.compile("\\[([^\\]]*)\\]");
Matcher m = regex.matcher(str);
if (m.find()) {
result = m.group();
}
Se você precisar que ele esteja no formato identifier + [ + content + ]
, poderá limitar a extração do conteúdo apenas quando o identificador for um alfanumérico:
[a-zA-Z][a-z-A-Z0-9_]*\s*\[([^\]]*)\]
Isso irá validar coisas como Foo [Bar]
, ou myDevice_123["input"]
por exemplo.
Problema principal
O principal problema é quando você deseja extrair o conteúdo de algo assim:
FOO[BAR[CAT[123]]+DOG[FOO]]
O Regex não funcionará e retornará BAR[CAT[123
e FOO
.
Se alterarmos o Regex para, \[(.*)\]
então estamos bem, mas, se você estiver tentando extrair o conteúdo de coisas mais complexas, como:
FOO[BAR[CAT[123]]+DOG[FOO]] = myOtherFoo[BAR[5]]
Nenhum dos Regexes funcionará.
O Regex mais preciso para extrair o conteúdo adequado em todos os casos seria muito mais complexo, pois seria necessário equilibrar []
pares e fornecer a eles o conteúdo.
Uma solução mais simples
Se seus problemas estão ficando complexos e o conteúdo do []
arbitrário, você pode equilibrar os pares de []
e extrair a string usando o código antigo simples e rathe do que um Regex:
int i;
int brackets = 0;
string c;
result = "";
for (i = input.indexOf("["); i < str.length; i++) {
c = str.substring(i, i + 1);
if (c == '[') {
brackets++;
} else if (c == ']') {
brackets--;
if (brackets <= 0)
break;
}
result = result + c;
}
Isso é mais pseudo-código do que código real, não sou um codificador Java, portanto não sei se a sintaxe está correta, mas deve ser fácil o suficiente para melhorar.
O que importa é que esse código funcione e permita que você extraia o conteúdo do []
, por mais complexo que seja.
Eu acho que sua expressão regular ficaria assim:
/FOO\[(.+)\]/
Supondo que o FOO seja constante.
Então, para colocar isso em Java:
Pattern p = Pattern.compile("FOO\\[(.+)\\]");
Matcher m = p.matcher(inputLine);
String input = "FOO[BAR]";
String result = input.substring(input.indexOf("[")+1,input.lastIndexOf("]"));
Isso retornará o valor entre o primeiro '[' e o último ']'
Foo [Bar] => Barra
Foo [Barra [teste]] => Barra [teste]
Nota: Você deve adicionar uma verificação de erro se a sequência de entrada não estiver bem formada.
Eu definiria que quero um número máximo de caracteres não-] entre [
e ]
. Eles precisam ser escapados com barras invertidas (e em Java, eles precisam ser escapados novamente), e a definição de não] é uma classe de caractere, portanto, interna [
e ]
(ie [^\\]]
). O resultado:
FOO\\[([^\\]]+)\\]
Assim funciona, se você deseja analisar alguma string que é proveniente de mYearInDB.toString () = [2013], ela dará 2013
Matcher n = MY_PATTERN.matcher("FOO[BAR]"+mYearInDB.toString());
while (n.find()) {
extracredYear = n.group(1);
// s now contains "BAR"
}
System.out.println("Extrated output is : "+extracredYear);
Este regexp funciona para mim:
form\[([^']*?)\]
exemplo:
form[company_details][0][name]
form[company_details][0][common_names][1][title]
resultado:
Match 1
1. company_details
Match 2
1. company_details
Testado em http://rubular.com/
"FOO[DOG]".replaceAll("^.*?\\[|\\].*", "");
Isso retornará uma string, levando apenas a string entre colchetes.
Isso remove toda a corda do lado de fora dos colchetes.
Você pode testar este código de amostra java on-line: http://tpcg.io/wZoFu0
Você pode testar esse regex aqui: https://regex101.com/r/oUAzsS/1