1. Diese Seite verwendet Cookies. Wenn du dich weiterhin auf dieser Seite aufhältst, akzeptierst du unseren Einsatz von Cookies. Weitere Informationen
  2. Unsere jährliche Weihnachts-Banner-Aktion hat begonnen! Wir freuen uns auf viele, viele kreative Vorschläge.
    Mehr dazu könnt Ihr hier nachlesen: Weihnachtsbanner 2016

    Information ausblenden

Reguläre Ausdrücke mit C++

Dieses Thema im Forum "OS X-Developer" wurde erstellt von snoopysalive, 24.06.07.

  1. snoopysalive

    snoopysalive Allington Pepping

    Dabei seit:
    19.08.05
    Beiträge:
    195
    Servus!

    Ich versuche schon ewigst, meinem OS X-GCC reguläre Ausdrücke beizubringen. Im Moment werkle ich mit Boost.Regex herum, bekomme aber kein Programm damit compiliert. Hier mal der Quellcode, den ich aus dem Boost-Tutorial habe:

    Code:
    #include <iostream>
    #include <string>
    #include <boost/regex.hpp>  // Boost.Regex lib
    
    using namespace std;
    
    int main( ) {
    
       std::string s, sre;
       boost::regex re;
    
       while(true)
       {
          cout << "Expression: ";
          cin >> sre;
          if (sre == "quit")
          {
             break;
          }
          cout << "String:     ";
          cin >> s;
    
          try
          {
             // Set up the regular expression for case-insensitivity
             re.assign(sre, boost::regex_constants::icase);
          }
          catch (boost::regex_error& e)
          {
             cout << sre << " is not a valid regular expression: \""
                  << e.what() << "\"" << endl;
             continue;
          }
          if (boost::regex_match(s, re))
          {
             cout << re << " matches " << s << endl;
          }
       }
    }
    
    Die Boost-Library habe ich mit dem typischen Dreiersatz "./configure, make, make install" in /usr/local/include/boost-1_34 installiert. Ergo müsste der Aufruf von

    Code:
    g++ -I /usr/local/include/boost-1_34 -o test test.cpp
    
    ausreichen, um das Programm (hier test.cpp) compilieren zu können. Tut es aber nicht. Der Linker meckert und meldet mir folgendes:

    Code:
    /usr/bin/ld: Undefined symbols:
    boost::basic_regex<char, boost::regex_traits<char, boost::cpp_regex_traits<char> > >::do_assign(char const*, char const*, unsigned int)
    boost::match_results<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, std::allocator<boost::sub_match<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > > > > >::maybe_assign(boost::match_results<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, std::allocator<boost::sub_match<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > > > > > const&)
    boost::re_detail::perl_matcher<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, std::allocator<boost::sub_match<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > > > >, boost::regex_traits<char, boost::cpp_regex_traits<char> > >::construct_init(boost::basic_regex<char, boost::regex_traits<char, boost::cpp_regex_traits<char> > > const&, boost::regex_constants::_match_flags)
    boost::re_detail::perl_matcher<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, std::allocator<boost::sub_match<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > > > >, boost::regex_traits<char, boost::cpp_regex_traits<char> > >::match()
    boost::re_detail::get_mem_block()
    boost::re_detail::put_mem_block(void*)
    boost::re_detail::raise_runtime_error(std::runtime_error const&)
    boost::re_detail::get_default_error_string(boost::regex_constants::error_type)
    boost::re_detail::cpp_regex_traits_implementation<char>::transform_primary(char const*, char const*) const
    boost::re_detail::cpp_regex_traits_implementation<char>::transform(char const*, char const*) const
    typeinfo for boost::regex_error
    collect2: ld gab 1 als Ende-Status zurück
    
    Ich werde daraus nicht schlau und wende mich nun an euch. Hat irgendwer von euch schon mal das Boost-Paket zum Laufen gebracht? Wenn ja, wie? Oder gibt es funktionierende Alternativen? Vielleicht sogar in der Standard-Bibliothek?

    Ich verwende jedenfalls GCC-Version 4.1.2, die C++ ansonsten anstandslos compiliert. Mit früheren Versionen hat es auch nicht geklappt.

    Ich bin für jede Anregung dankbar.

    Gruß,
    Matthias
     
  2. Bölzebub

    Bölzebub Querina

    Dabei seit:
    27.05.05
    Beiträge:
    180
    Ich glaube, du musst g++ nur sagen, dass es Boost bzw. Boost.Regexp dazulinken soll. Ist jetzt geraten (ich hab keine Ahnung von C++ und Boost), aber probier es mal mit -lboost.
     
  3. tjp

    tjp Baldwins roter Pepping

    Dabei seit:
    07.07.04
    Beiträge:
    3.245
    Es fehlt sehr wahrscheinlich noch der Pfad, den man mit "-L" übergibt. Bei mir sähe das dann wie folgt aus (boost ist an anderer Stelle installiert).
    Code:
    g++ -L/opt/local/lib -lboost_regex -I/opt/local/include/boost -o test test.cpp
    
     
  4. snoopysalive

    snoopysalive Allington Pepping

    Dabei seit:
    19.08.05
    Beiträge:
    195
    Mit diesem Aufruf wird's besser:
    Code:
    g++ -I /usr/local/include/boost-1_34 -o test test.cpp /usr/local/lib/libboost_regex-d.a
    Danach habe ich aber noch immer kein lauffähiges Programm, denn der Linker findet noch immer irgendwas nicht:

    Code:
    /usr/bin/ld: Undefined symbols:
    std::basic_string<char, std::char_traits<char>, std::allocator<char> >::_Rep::_S_create(unsigned long, std::allocator<char> const&)
    std::__default_alloc_template<true, 0>::deallocate(void*, unsigned long)
    std::__default_alloc_template<true, 0>::allocate(unsigned long)
    collect2: ld gab 1 als Ende-Status zurück
    Seh ich das richtig, dass der Linker anscheinend Probleme mit Strings hat? Was muss ich da noch ändern, damit das Programm endlich compiliert?

    Danke,
    Matthias
     
  5. tjp

    tjp Baldwins roter Pepping

    Dabei seit:
    07.07.04
    Beiträge:
    3.245
    Nein, der Aufruf ist so nicht richtig, Du mußt schon die Library wie von mir beschrieben gegen das Programm linken.
     
  6. snoopysalive

    snoopysalive Allington Pepping

    Dabei seit:
    19.08.05
    Beiträge:
    195
    Ok, ich habe den Aufruf

    Code:
    g++ -I/usr/local/include/boost -L/usr/local/lib -lboost_regex-gcc-1_34 -o test test.cpp
    
    Nun schon mehrfach ausprobiert. Die Compilerausgabe bleibt bei
    Code:
    /usr/bin/ld: Undefined symbols:
    boost::basic_regex<char, boost::regex_traits<char, boost::cpp_regex_traits<char> > >::do_assign(char const*, char const*, unsigned int)
    boost::match_results<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, std::allocator<boost::sub_match<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > > > > >::maybe_assign(boost::match_results<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, std::allocator<boost::sub_match<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > > > > > const&)
    boost::re_detail::perl_matcher<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, std::allocator<boost::sub_match<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > > > >, boost::regex_traits<char, boost::cpp_regex_traits<char> > >::construct_init(boost::basic_regex<char, boost::regex_traits<char, boost::cpp_regex_traits<char> > > const&, boost::regex_constants::_match_flags)
    boost::re_detail::perl_matcher<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, std::allocator<boost::sub_match<__gnu_cxx::__normal_iterator<char const*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > > > >, boost::regex_traits<char, boost::cpp_regex_traits<char> > >::match()
    boost::re_detail::get_mem_block()
    boost::re_detail::put_mem_block(void*)
    boost::re_detail::raise_runtime_error(std::runtime_error const&)
    boost::re_detail::get_default_error_string(boost::regex_constants::error_type)
    boost::re_detail::cpp_regex_traits_implementation<char>::transform_primary(char const*, char const*) const
    boost::re_detail::cpp_regex_traits_implementation<char>::transform(char const*, char const*) const
    typeinfo for boost::regex_error
    collect2: ld gab 1 als Ende-Status zurück
    
    Hört sich für mich so an, als würde der Compiler überhaupt gar nichts finden. An was könnte es denn noch liegen?

    Gruß,
    Matthias
     
  7. tjp

    tjp Baldwins roter Pepping

    Dabei seit:
    07.07.04
    Beiträge:
    3.245
    Ich habe es bei mir, wie ich es beschrieben habe, compiliert und gelinkt, funktioniert einwandfrei! Bist Du Dir sicher, daß die Installation von boost auch korrekt ist?
     
  8. snoopysalive

    snoopysalive Allington Pepping

    Dabei seit:
    19.08.05
    Beiträge:
    195
    Ich habe jetzt Boost mehrfach neu compiliert und installiert. Wenn ich mal den GCC 4.1.2 hintenanstelle und stattdessen auf die Version 3.3 setze, fällt mir plötzlich auf, dass weniger Skips beim Compilieren stattfinden. Der Computer compiliert auch länger. Ergo darf man Boost mit keiner GCC-Version >3 compilieren.

    Allerdings gibt es dann noch immer Skips, sodass die Bibliothek immer noch nicht vollständig compiliert und installiert wird.

    Mir ist es jetzt zu blöd geworden und habe nochmal mein Glück mit PCRE versucht. Das läuft jetzt und ist mit dem header pcrecpp.h fast genauso komfortabel wie in den Skript-Sprachen.

    Dennoch, vielen Dank, tjp, für deine vielen Tipps. Ich habe zumindest wieder was hinzugelernt.

    Allerdings habe ich auch gleich wieder eine weitere Frage zu Hash-Maps. Dazu mache ich aber einen neuen Thread auf.

    Grüße,
    Matthias
     
  9. tjp

    tjp Baldwins roter Pepping

    Dabei seit:
    07.07.04
    Beiträge:
    3.245
    Ah, da kommen wir der Sache doch näher! Du mußt unbedingt aufpassen, daß Du exakt denselben C++ Compiler für die Boost Compilierung benutzt, wie Du später für den Projekt nimmst. Daher kommen auch die Linker-Fehler bei Dir!
    Nimm den g++ von MacOS X und compiliere damit boost UND dein Projekt.

    Der aktuelle g++ ist immer noch 4.0.1 und befindet sich "/usr/bin/g++", sofern Du die Developer Tools installiert hast (solltest Du, oder etwa nicht?)
     
  10. snoopysalive

    snoopysalive Allington Pepping

    Dabei seit:
    19.08.05
    Beiträge:
    195
    Da gebe ich dir auch Recht, allerdings habe ich das schon ausprobiert. Ich habe also sowohl Boost als auch mein Projekt mit dem g++ unter /usr/bin compiliert. Fehlanzeige. Und bei mir das eben noch Version 3.3, obwohl ich die Developer Tools drauf hab. Aber gut, vielleicht sollte ich die mal updaten. Hier mal die Ausgabe:

    Code:
    /usr/bin/g++ -v
    Reading specs from /usr/libexec/gcc/darwin/ppc/3.3/specs
    Thread model: posix
    gcc version 3.3 20030304 (Apple Computer, Inc. build 1819)
    
    Na ja, solange es jetzt aber mit pcre geht, bin ich ja eh schon zufrieden.
     

Diese Seite empfehlen