Java RegEx

Split1989

hh-student.de
ID: 238425
L
9 April 2007
1.223
85
hallo leute,

hab wiedermal ein kleines problem

will in java mit hilfe einer regular expression € und cent beträge auslesen... funzt aber noch nicht ganz so wie ich will

Code:
String string = "5,51€";
        Pattern pattern = Pattern.compile("(\\d*)(\\D*)(\\d*)(\\D*)");
        java.util.regex.Matcher matcher = pattern.matcher(string);

        List<String> bigger = new ArrayList<String>();
        List<String> small = new ArrayList<String>();

        while(matcher.find())
        {
            bigger.add(matcher.group(1));
            small.add(matcher.group(3));
        }

            System.out.println("€: "+bigger.get(0));
            System.out.println("ct: "+small.get(0));

er soll aber auch
Code:
String string = "51ct";
als cent erkennen und nicht als €

das ganze soll ohne if abfrage geschehen sondern nur durch umformung der regular expression.
auch soll nicht nach "ct" geprüft werden ....

habt ihr da ne idee?
 
wäre in dem format natürlich möglich,

aber es soll auch

5€ 20ct

erkannt werden :(

mit der if abfrage würde das so aussehen

Code:
String string = "5,51€";
        Pattern pattern = Pattern.compile("(\\d*)(\\D*)(\\d*)(\\D*)");
        java.util.regex.Matcher matcher = pattern.matcher(string);

        List<String> big = new ArrayList<String>();
        List<String> small = new ArrayList<String>();

        while(matcher.find())
        {
            String smaller = matcher.group(3);
            String bigger = matcher.group(1);
            if(smaller.length() == 0){smaller = bigger; bigger = "0";}
            small.add(smaller);
            big.add(bigger);
        }
            int wert = new Integer(big.get(0))*100+new Integer(small.get(0));
            System.out.println(wert);

edit:
Hab das jetzt erstmal so gelöst, da mich die einzelnen werte ansich garnicht interresieren sondern nur der cent betragm aber leider geht jetzt sowas wie 5,5€ nicht .... das wäre zwar noch schön aber ist nicht zwingend notwendig.
Code:
public static void main(String[] args) {
        // TODO code application logic here
		System.out.println(RegExWert2("5,50€"));
    }
	public static long RegExWert2(String string){
		long wert = new Integer(string.replaceAll("(\\d*)(\\D*)(\\d*)(\\D*)", "$1$3"));
		return wert;
	}
 
Zuletzt bearbeitet:
Ich seh in dem RegExp weder die Buchstaben "ct", noch das Zeichen "€". D.h. da stimmt gewaltig was ned ;)
 
Ich seh in dem RegExp weder die Buchstaben "ct", noch das Zeichen "€". D.h. da stimmt gewaltig was ned ;)

soll auch kein € und kein ct stehen ;)

er soll nähmlich später auch andere währungen auslesen ohne das man den RegExp anpassen muss.
zb.: 70 ₤ 67p


die prüfung was für eine währung das ist kommt dann später mittels

Code:
public static String RegExWaehrung(String string) {
        string = string.replaceAll(" ", "");
        String w1 = string.replaceAll("(\\d*)(\\D*)(\\d*)(\\D*)", "$2");
        String w2 = string.replaceAll("(\\d*)(\\D*)(\\d*)(\\D*)", "$4");
        return (",".equals(w1))? w2:w1;
    }


und dann wird noch geprüft ob die Währung bekannt ist (mittells des ausgelesenen strings)
 
Der Code sieht auch mehr als kryptisch aus... ich mach das mit einem RegExp 8O

  • Was is denn eine Währung bei dir? Eine beliebige Kombination aus Nicht-Ziffer-Zeichen?
  • Warum wechselt du \D und \d zweimal ab? Also warum hast du 4 Blöcke? Bei mir hat so ein String nur zwei Blöcke, nämlich den Betrag und die Währung.
  • Wieso hast du als Quantifier überall n Stern? Der Leerstring is wohl kein ordentlicher Betrag. Und der String "foo" wohl auch nicht, weil die Ziffern fehlen.
Bau zwei Blöcke (Betrag und Währung) und fordere von beiden, dass auch was drinsteht, sonst is die Eingabe ja falsch. Ein replaceAll() brauchst du gar nicht ;)
 
Währung -> wird später ein Object sein mit werten big und small Bsp.(big = "€" small = "ct")

string = string.replaceAll(" ", ""); mache ich dafür damit auch sowas eigegeben werden kann "2 € 12 ct";


Code:
String w1 = string.replaceAll("(\\d*)(\\D*)(\\d*)(\\D*)", "$2");
String w2 = string.replaceAll("(\\d*)(\\D*)(\\d*)(\\D*)", "$4");
return (",".equals(w1))? w2:w1;

hier soll "2,12" "12 12 ct" und "148ct" abgefangen werden.


hab das jetzt dazu geändert.
Code:
public static long RegExWert2(String string) {
        string = string.replaceAll(" ", "");
        long wert = new Integer(string.replaceAll("(\\d*)(\\D)(\\d{1,2})(\\D)", "$1$3"));
        return wert;
    }
    
public static String RegExWaehrung(String string) {
        string = string.replaceAll(" ", "");
        String w1 = string.replaceAll("(\\d*)(\\D)(.*)", "$2");
        String w2 = string.replaceAll("(.*)(\\d{1,2})(\\D)", "$3");
        return (",".equals(w1))? w2:w1;
}

manchmal interessieren mich nur die zahlen, manchmal die währung.

was hättest du denn für einen vorschlag?
 
Währung -> wird später ein Object sein mit werten big und small Bsp.(big = "€" small = "ct")
Wie du das abspeicherst, interessiert den RegExp nicht.
string = string.replaceAll(" ", ""); mache ich dafür damit auch sowas eigegeben werden kann "2 € 12 ct";
Für was nimmst du dann einen RegExp, wenn du effektiv Handarbeit machst? Is dann ja sinnfrei.
was hättest du denn für einen vorschlag?
Ordentlich halt den regulären Ausdruck schreiben und nicht zusätzliche Logik durch nachträgliches Ersetzen von irgendwelchen Zeichen machen.

Wenn du Leerzeichen zwischen Betrag und Währung tippen können möchtest, schreib dann in den RegExp, dafür gibts ihn ja.

Ein Beispiel (vereinfacht, du willst sicher auch Dezimalbrüche und Non-Word-Characters):
Code:
RegExp: ((\d+)\s?(\w+)\s+){1,2}
Eingaben:
"2 EUR" -> Match
"233eur" -> Match
"42 eur 4 ct" -> Match
"42eur 7x" -> Match
"42eur7x" -> NO Match
"EUR" -> NO match
"42 711 ct" -> NO match
"43" -> NO match
"1 a 2 b 3 c" -> NO match
"4 eur ct" -> NO match
 
Zuletzt bearbeitet:
irgendwie funktioniert deine expression nicht bei mir

hier ist jetzt meiner, was hällst du von ihm?
sollte eigentlich alles abdecken oder?

Code:
public static long RegExWert2(String string) {
        long wert = new Integer(string.replaceAll("(\\d+)(\\s*)(\\D+)(\\d{0,2})(\\s*)(\\D*)", "$1$4"));
        return wert;
    }
    
    public static String RegExWaehrung(String string) {
        String w1 = string.replaceAll("(\\d+)(\\s*)(\\D+)(\\d{0,2})(\\s*)(\\D*)", "$3");
        String w2 = string.replaceAll("(\\d+)(\\s*)(\\D+)(\\d{0,2})(\\s*)(\\D*)", "$6");
        return (",".equals(w1))? w2:w1;
    }
 
Copy&Paste funktioniert nie. a) hatte ich n Blackslash vergessen, b) is der RegExp eh nicht zu copy&pasten, sondern zum Verstehen da. c) blick ich immer noch ned, wieso du für eine Sache 3 RegExp und diverse Replace-Aufrufe brauchst.

\D seh ich problematisch, weil \D eben auch \s einschließt und du somit nicht mehr durchblickst, wenn du beide kombinierst.
 
\D benutze ich weil \w doch kein € beinhaltet oder?

vllt gefällt dir der code besser
Code:
Pattern pattern = Pattern.compile("(\\d+)(\\s*)(\\D+)(\\s*)(\\d{0,2})(\\s*)(\\D*)");
Matcher matcher = pattern.matcher(string);
ArrayList<String> arry = new ArrayList<String>();

while (matcher.find()) {
   arry.add(matcher.group(1));
   arry.add(matcher.group(5));
   arry.add(matcher.group(3));
   arry.add(matcher.group(7));  
}

jetzt kann man mit arry.get(i); auf die einzelnen elemente zugreifen
 
\D benutze ich weil \w doch kein € beinhaltet oder?
Richtig. Mein Code war ja nur ein Beispiel. Mir persönlich gefällt das pauschale \w halt nicht direkt am \s, weil alle Leerzeichen von \w, also auch von \s gecaptured werden können. Natürlich funktioniert es richtig, weil nach Gready-Verfahren das \s die Spaces kriegt und im \w dann keine mehr drin sind; is aber imo halt unübersichtlich.

Zum anderen hattest du ja eh gesagt, dass du n Objekt Währung hast, was die beiden möglichen Einheiten hat, d.h. du wirst wohl eh den RegExp dynamisch bauen und so deine möglichen Währungen statt dem \w einsetzen.
vllt gefällt dir der code besser
Is kürzer und verständlicher. Lass jetzt noch die Klammern im RegExp weg, wo du die Inhalte eh nicht brauchst, dann sind deine Zugriffe über die Gruppen auch 1, 2, 3, 4 und nicht so komisch 1, 3, 5, 7.

Statt der ArrayList würd ich auch 4 separate Variablen nehmen. Ob ich jetzt in deinem Beispiel matcher.group(5) nehm oder dann arry.get(1) hab ich so oder so keine Ahnung, was das jetzt sein soll.