Expressão Regular Alfanumerico + espaço + acentuação

Olá a todos,

   Estou montando um medodo que recebe uma string nessa string contem caracteres especiais e acentuação, estou montando expressão regular para resolver o meu problema.

Olhei a API do java e vi que o /W resolve o meu problema porém ele remove os espaços em branco e caracteres acentuados. Então pesquisei no google e vi sobre Diacritic http://en.wikipedia.org/wiki/Diacritic pórem não achei nada para o java.

Minha dúvida é se tem alguma forma de eu fazer isso? Eu estava pensando em fazer varios replaces mas creio que nao fica muito bom…

Obrigado

Me expressei mau ou vocês conseguiram me entender?

Qual é seu problema? Mostre uma entrada e uma saída para sabermos o que você quer fazer.

Exemplo:

String s = "Gisele Bündchen da Conceição Nascimento";
String t = funcao (s);
System.out.println (t);

a) t = “Gisele Bundchen da Conceicao Nascimento”

b) t = “GISELEBÜNDCHENDACONCEICAONASCIMENTO”

c) t = “Gisele”

d) t = “Gisele Buendchen da Conceic/a~o Nascimento”

Marque a alternativa desejada.

Eu preciso que os dados de saida fiquem igual a letra:

a) t = “Gisele Bundchen da Conceicao Nascimento”

Porem acontece o seguinte caso tambem:

String rua="Av. Andrómêda, 2247 - SP"

Saida = “Av Andromeda 2247 SP” (Esse nome nao contem acento coloquei apenas p demostração)

Fica mais facil demostrar com endereços pois contem caracteres especiais e acentos.

Deu para entender meu problema? :lol:

[code]import java.util.regex.*;

public class RegexRemoverAcentos
{
public static void main( String args[] )
{
String texto = “Av. Andrómêda, 2247 - SP” ;
Pattern regra = Pattern.compile( “[\p{Alnum} ]” );

    String saida = "";
    
    for( int i = 0; i < texto.length(); i++ )
    {
        Matcher mt = regra.matcher( Character.toString( texto.charAt( i ) ) );
        if( mt.matches() )
        {
            saida += mt.group();
        }else{
            if( !( Character.isLetter( texto.charAt( i ) ) ) )
            {
                continue;
            }
            
            String aux = Character.toString( texto.charAt( i ) );
            boolean upperCaseFlag = false;
            
            if( Character.isUpperCase( aux.charAt( 0 ) ) )
            {
                upperCaseFlag = true;
                aux = aux.toLowerCase();
            }
            
            aux = aux.replace( 'à', 'a' );
            aux = aux.replace( 'è', 'e' );
            aux = aux.replace( 'ì', 'i' );
            aux = aux.replace( 'ò', 'o' );
            aux = aux.replace( 'ù', 'u' );
            
            aux = aux.replace( 'á', 'a' );
            aux = aux.replace( 'é', 'e' );
            aux = aux.replace( 'í', 'i' );
            aux = aux.replace( 'ó', 'o' );
            aux = aux.replace( 'ú', 'u' );
            
            aux = aux.replace( 'â', 'a' );
            aux = aux.replace( 'ê', 'e' );
            aux = aux.replace( 'î', 'i' );
            aux = aux.replace( 'ô', 'o' );
            aux = aux.replace( 'û', 'u' );
            
            aux = aux.replace( 'ã', 'a' );
            aux = aux.replace( 'õ', 'o' );

            aux = aux.replace( 'ä', 'a' );
            aux = aux.replace( 'ë', 'e' );
            aux = aux.replace( 'ï', 'i' );
            aux = aux.replace( 'ö', 'o' );
            aux = aux.replace( 'ü', 'u' );
            
            aux = aux.replace( 'ç', 'c' );
            
            
            if( upperCaseFlag )
            {
                
                aux = aux.toUpperCase();
                
            }
            
            saida += aux;                
        }
    }
    System.out.println( saida );
}

}[/code]

Implementei isso aqui… não é uma forma muito elegante de resolver o problema, e acredito que haja meio muito mais simples e lógico, mas essa aí resolve…
Não me preocupei com otimizações =P

Olá agradeço pelas respostas Carnevalli e thingol.

Carnevalli eu pensei fazer isso mas ocorre de ter varios nomes serem grandes percorrer a caracter por caracter vai resolver o problema porem o que vou gerar vai ser um serviço de correção dessas regras, dai preciso um pouco de performace por nao sei quantas pessoas vao utilizar.

Eu estava pensando fazer algo assim :

                // Remove todos . da string
		ret = ret.replaceAll("\\.?", "");
		// Remove todas , da string
		ret = ret.replaceAll(",?", "");
		// Remove todas - da string
		ret = ret.replaceAll("-?", "");
		// Remove todas : da string		
		ret = ret.replaceAll(":?", "");
		// Remove todas ( da string
		ret = ret.replaceAll("\\(?", "");
		// Remove todas ) da string
		ret = ret.replaceAll("\\)?", "");
		// Remove todas ª da string
		ret = ret.replaceAll("ª?", "");
		// Remove todas | da string
		ret = ret.replaceAll("\\|?", "");
		// Remove todas \ da string		
		ret = ret.replaceAll("\\\\?", "");
		// Remove todas º da string
		ret = ret.replaceAll("º?", ""); // ESSE NAO CONSEGUI FAZER FUNCIONAR
		
		// Passar o nome para maiúsculas
		//ret = endereco.toUpperCase();
		
		// Trocar os espaços duplicados, tabulações etc. por um espaço
		ret = ret.replaceAll("\\s+", " ");
		// Remover o espaço no início
		ret = ret.replaceAll("^\\s+", "");
		// Remover o espaço no fim
		ret = ret.replaceAll("\\s+$", "");

Esse é os caracteres que consegui identificar no banco no caso eu estava pensando armazenar tudo em um array e rodar um for com esses caracteres especiais + os caracteres acentuados, será que ficaria melhor a performace e seria correto ?

Agradeço.

Eu tenho uma solução mais rápida para seu problema. Não tem nada de expressão regular ou coisas esdrúxulas e lentas. Não consigo imaginar uma solução mais rápida, na verdade.

class RemoverAcentos {
    static String acentuado = &quot;çÇáéíóúýÁÉÍÓÚÝàèìòùÀÈÌÒÙãõñäëïöüÿÄËÏÖÜÃÕÑâêîôûÂÊÎÔÛ&quot;;
    static String semAcento = &quot;cCaeiouyAEIOUYaeiouAEIOUaonaeiouyAEIOUAONaeiouAEIOU&quot;;
    static char[] tabela;
    static {
        tabela = new char[256];
        for (int i = 0; i &lt; tabela.length; ++i) {
	    tabela [i] = (char) i;
        }
        for (int i = 0; i &lt; acentuado.length(); ++i) {
            tabela [acentuado.charAt(i)] = semAcento.charAt(i);
        }
    }
    public static String remover (final String s) {
        StringBuffer sb = new StringBuffer();
        for (int i = 0; i &lt; s.length(); ++i) {
            char ch = s.charAt (i);
            if (ch &lt; 256) { 
                sb.append (tabela [ch]);
            } else {
                sb.append (ch);
            }
        }
        return sb.toString();
    }
    public static void main(String[] args) {
        String s = &quot;Gisele Bündchen da Conceição e Silva foi batizada assim em homenagem à sua conterrânea de Horizontina, RS.&quot;;
        s = RemoverAcentos.remover (s);
        System.out.println (s);
    }
}

Olá Thingol gostei dessa logica que me mandou vou até fazer uma junção da classe que eu fiz :


/**
 * @author Fnascimento
 *
 * Classe de normalização de String.
 * Remove acentuação, caracteres especiais, 
 *  espaços duplicado, espaços do inicio e fim da string.
 *  
 */

public class NormalizaString {
	
	public String normalizar(String str) {
		
		/** Troca os caracteres acentuados por não acentuados **/
		String[][] caracteresAcento = {
				{"Á", "A"}, {"á", "a"},
				{"É", "E"}, {"é", "e"},
				{"Í", "I"}, {"í", "i"},
				{"Ó", "O"}, {"ó", "o"},
				{"Ú", "U"}, {"ú", "u"},
				{"À", "A"}, {"à", "a"},
				{"È", "E"}, {"è", "e"},
				{"Ì", "I"}, {"ì", "i"},
				{"Ò", "O"}, {"ò", "o"},
				{"Ù", "U"}, {"ù", "u"},
				{"Â", "A"}, {"â", "a"},
				{"Ê", "E"}, {"ê", "e"},
				{"Î", "I"}, {"î", "i"},
				{"Ô", "O"}, {"ô", "o"},
				{"Û", "U"}, {"û", "u"},
				{"Ä", "A"}, {"ä", "a"},
				{"Ë", "E"}, {"ë", "e"},
				{"Ï", "I"}, {"ï", "i"},
				{"Ö", "O"}, {"ö", "o"},
				{"Ü", "U"}, {"ü", "u"},
				{"Ã", "A"}, {"ã", "a"}, 
				{"Õ", "O"}, {"õ", "o"},
				{"Ç", "C"}, {"ç", "c"},
		};
		
		for (int i = 0; i < caracteresAcento.length; i++) {
			str = str.replaceAll(caracteresAcento[i][0], caracteresAcento[i][1]);
        }
		
		/** Troca os caracteres especiais da string por "" **/
		String[] caracteresEspeciais = {"\\.", ",", "-", ":", "\\(", "\\)", "ª", "\\|", "\\\\", "°"};
		
		for (int i = 0; i < caracteresEspeciais.length; i++) {
			str = str.replaceAll(caracteresEspeciais[i], "");
        }

		/** Troca os espaços no início por "" **/
		str = str.replaceAll("^\\s+", "");
		/** Troca os espaços no início por "" **/
		str = str.replaceAll("\\s+$", "");
	    /** Troca os espaços duplicados, tabulações e etc por  " " **/
		str = str.replaceAll("\\s+", " ");
	    
		return str;
	}
}

Agradeço por ter ajudado.

Agora so continuar implementando o sisteminha

vlw.

Olá!

recentemente tive que resolver um problema desses e fazendo algumas buscas cheguei na seguinte implementação:

    public String removerAcentos(String acentuada) {
        CharSequence cs = new StringBuilder(acentuada);
        return Normalizer.normalize(cs, Normalizer.Form.NFKD).replaceAll("\\p{InCombiningDiacriticalMarks}+", "");
    }

testa ai e vê se resolve.

2 curtidas

Parabéns!!! Muito boa essa implementação… Resolveu meu problema de forma bem simplificada.

Muito bom m0sk4 , me ajudou bastante aqui em uma implementação.
Obrigado por compartilhar.

PERFEITO!!!

Muito obrigado m0sk4! melhor solução e mais simples!

Bom trabalho e que Deus abençoe a sua vida e família!