Re: [Talk-de] PERL REGEX?

2008-10-16 Diskussionsfäden Dirk Stöcker

On Thu, 16 Oct 2008, Jacques Nietsch wrote:


Warum benutzt hier eigendlich keiner XML::Parser zum Parsen vom osm
Dateien?


RegEx kann ich im Schlaf, XML::Parser müsste ich nachschauen :-)

Ciao
--
http://www.dstoecker.eu/ (PGP key available)___
Talk-de mailing list
Talk-de@openstreetmap.org
http://lists.openstreetmap.org/listinfo/talk-de


Re: [Talk-de] PERL REGEX?

2008-10-16 Diskussionsfäden Frederik Ramm
Hallo,

Jacques_N wrote:
> Was ich mit diesem Posting eigendlich sagen wollte: man muß nicht immer  
> das Rad neu erfinden,
> es gibt Leute, die das schon gemacht haben und oft auch viel besser als  
> man es selbst könnte.

Das stimmt.

Allerdings kann man, indem man "cheatet", ein OSM-XML-File unter 
Umstaenden wesentlich schneller parsen als das jeder Parser koennte, 
denn man weiss bestimmte Dinge, die der Parser nicht weiss. Zum Beispiel 
weiss man, dass in einem "lat"- oder "lon"-Attribut niemals ein 
UTF8-Umlaut vorkommen kann, und daher kann man es sich sparen, die Werte 
dieser Attribute nach UTF8 zu parsen. Oder man interessiert sich 
vielleicht nur fuer Nodes in einem bestimmten Koordinatenbereich; ein 
gewoehnlicher XML-Parser, auch SAX, hat schon username, id, lat, lon 
geparst und schoen in ein Hash geschrieben und dafuer extra Speicher 
alloziert, bevor das Programm die Chance hat, zu sagen "nee, dieser Node 
interessiert mich nicht".

Also, ein fertiger XML-Parser bietet sich immer dann an, wenn man eh die 
ganze Datei verarbeiten will oder es auf die Ausfuehrungsgeschwindigkeit 
nicht so ankommt. Wenn man dann am Ende noch von 2 Stunden 
Ausfuehrungszeit auf 1 Stunde Ausfuehrungszeit runter will, kann man 
immer noch von Hand parsen.

Bye
Frederik

-- 
Frederik Ramm  ##  eMail [EMAIL PROTECTED]  ##  N49°00'09" E008°23'33"

___
Talk-de mailing list
Talk-de@openstreetmap.org
http://lists.openstreetmap.org/listinfo/talk-de


Re: [Talk-de] PERL REGEX?

2008-10-16 Diskussionsfäden Jacques_N
Am 16.10.2008, 14:10 Uhr, schrieb Tobias Wendorff  
<[EMAIL PROTECTED]>:

> Jacques Nietsch schrieb:
>> Warum benutzt hier eigendlich keiner XML::Parser zum Parsen vom osm
>> Dateien?
>
> Frage war zwar nicht an mich, aber:
>
> Ich habe mit XML-Parsern immer schlechte Erfahrungen gemacht.
> Manche, wie XML Starlet, lesen erst die ganze XML-Datei ein
> und erzeugen das Inhaltsverzeichnis.

Ich sprach hier nicht von einem eigenständigen XML Parser, sondern von  
einem Perl Modul.
'XML::Parser' ist ein SAX Parser, also hält er nur den aktuellen Node im  
Speicher.
Nebenbei dieser Parser ist von Larry Wall geschrieben, dem Erfinder von  
Perl, das
sollte für eine gewisse Qualität bürgen ;-)

> Daher gehe ich Zeile für Zeile (im Stream) vor und arbeite
> rekursiv. Ich habe dadurch massive Verbesserungen in
> Performance und Geschwindigkeit bemerkt.
> Auch sinnvoll ist es, die OSM-Datei vorher in den Speicher
> zu laden und dann davon zu arbeiten, so "blinkt" die
> Festplatte nicht immer auf.

Das Beispielscript erzeugt eine Userliste, mit der Anzahl der Objekte nach  
Namen sortiert
in ca. 8 Sekunden aus einer 39 MB großen OSM Datei (XP 1GB 3GHz).
Die Festplatte blinkt dabei nicht viel mehr als sonst.

Was ich mit diesem Posting eigendlich sagen wollte: man muß nicht immer  
das Rad neu erfinden,
es gibt Leute, die das schon gemacht haben und oft auch viel besser als  
man es selbst könnte.

Jacques


___
Talk-de mailing list
Talk-de@openstreetmap.org
http://lists.openstreetmap.org/listinfo/talk-de


Re: [Talk-de] PERL REGEX?

2008-10-16 Diskussionsfäden Birgit Nietsch
Tobias Wendorff schrieb:

> Jacques Nietsch schrieb:
>> Warum benutzt hier eigendlich keiner XML::Parser zum Parsen vom
>> osm Dateien?
> 
> Frage war zwar nicht an mich, aber:
> 
> Ich habe mit XML-Parsern immer schlechte Erfahrungen gemacht.

Hier ist aber kein XML-Parser gemeint, sondern das Perl-Modul 
mit dem Namen XML::Parser. Das tut nichts weiter als dir ein
paar nette zusätzliche Perl-Funktionen zur Verfügung zu stellen,
die dir das Gehampel mit den regulären Ausdrücken abnehmen.

> Manche, wie XML Starlet, lesen erst die ganze XML-Datei ein
> und erzeugen das Inhaltsverzeichnis.

Das ist auch besser so. XML ist formatfrei, Einträge können
Zeilenumbrüche enthalten. 


___
Talk-de mailing list
Talk-de@openstreetmap.org
http://lists.openstreetmap.org/listinfo/talk-de


Re: [Talk-de] PERL REGEX?

2008-10-16 Diskussionsfäden Dirk Stöcker

On Thu, 16 Oct 2008, Tobias Wendorff wrote:


Auch sinnvoll ist es, die OSM-Datei vorher in den Speicher
zu laden und dann davon zu arbeiten, so "blinkt" die
Festplatte nicht immer auf.


Unter Linux würde ich hier mmap() empfehlen. Da kümmert sich dann der 
Kernel darum welche Teile in den Speicher sollen und regelt den 
Speicherbedarf dynamisch.


Ciao
--
http://www.dstoecker.eu/ (PGP key available)___
Talk-de mailing list
Talk-de@openstreetmap.org
http://lists.openstreetmap.org/listinfo/talk-de


Re: [Talk-de] PERL REGEX?

2008-10-16 Diskussionsfäden Tobias Wendorff
Jacques Nietsch schrieb:
> Warum benutzt hier eigendlich keiner XML::Parser zum Parsen vom osm  
> Dateien?

Frage war zwar nicht an mich, aber:

Ich habe mit XML-Parsern immer schlechte Erfahrungen gemacht.
Manche, wie XML Starlet, lesen erst die ganze XML-Datei ein
und erzeugen das Inhaltsverzeichnis.

Daher gehe ich Zeile für Zeile (im Stream) vor und arbeite
rekursiv. Ich habe dadurch massive Verbesserungen in
Performance und Geschwindigkeit bemerkt.

Auch sinnvoll ist es, die OSM-Datei vorher in den Speicher
zu laden und dann davon zu arbeiten, so "blinkt" die
Festplatte nicht immer auf.

___
Talk-de mailing list
Talk-de@openstreetmap.org
http://lists.openstreetmap.org/listinfo/talk-de


Re: [Talk-de] PERL REGEX?

2008-10-16 Diskussionsfäden Jacques Nietsch
Am 15.10.2008, 20:47 Uhr, schrieb GS  
<[EMAIL PROTECTED]>:

Warum benutzt hier eigendlich keiner XML::Parser zum Parsen vom osm  
Dateien?

> Hi,
>
> ich habe:
>
>  my ($v) = ($line =~ /^.+v=[\'\"]([\/-\w\d\s\.:,\(\)]+)[\'\"]/);
>
> Ich will aber einfach nur den Text zwischen den Anführungszeichen mit  
> allem
> drum und dran. Probleme gibt es mit den dt. Umlauten.
>
> (.+) läuft nicht, warum?
>
> Tnx
>
> Gerhard

Beispielscript das alle Usernamen aus nodes und ways extrahiert:
-
#!/usr/bin/perl

use XML::Parser;
my %Users = ();

sub StartHandler
{
my ( $expat, $tag, %attr ) = @_;

if( $tag eq 'node' or $tag eq 'way' )
{
$Users{ $attr{ 'user' } }++;
}
}

my $parser = new XML::Parser(Handlers => {Start => \&StartHandler });

$parser->parsefile( 'hamburg.osm', ErrorContext => 3 );

foreach my $user ( sort keys %Users )
{
print $user, ' - ', $Users{ $user } , "\n";
}
-

So etwas kann auch xml parsen, wenn mal mehr als ein Tag in einer Zeile ist

Jacques


___
Talk-de mailing list
Talk-de@openstreetmap.org
http://lists.openstreetmap.org/listinfo/talk-de


Re: [Talk-de] PERL REGEX?

2008-10-16 Diskussionsfäden Frederik Ramm
Hallo,

On 16.10.2008, at 09:42, [EMAIL PROTECTED] wrote:
> es geht so nicht...
> REGEX ist nun:
> my ($v) = ($line =~ /v=[\'\"](.*)[\'\"]/) ;
> Fehler...
> NEW REGEX ERROR reading osm file frankfurt0.osm, line follows  
> (expecting
> node or k/v for way):
> 

Kannst Du bitte mal den kompletten Code-Ausschnitt posten -  
insbesondere interessiert mich, wie vom Rueckgabewert auf "NEW REGEX  
ERROR" geschlossen wird, das muss ja irgendwo stehen. Wenn da zum  
Beispiel stuende

if (!$v) {
printf "NEW REGEX ERROR...\n";
}

dann wuerde mich nichts wundern, denn bei $v="0" wie in Deinem  
Beispiel wuerde dann ja ein Error ausgegeben.

Bye
Frederik

-- 
Frederik Ramm  ##  eMail [EMAIL PROTECTED]  ##  N49°00'09" E008°23'33"




___
Talk-de mailing list
Talk-de@openstreetmap.org
http://lists.openstreetmap.org/listinfo/talk-de


Re: [Talk-de] PERL REGEX?

2008-10-16 Diskussionsfäden Dirk Stöcker

On Thu, 16 Oct 2008, [EMAIL PROTECTED] wrote:


es geht so nicht...

REGEX ist nun:

my ($v) = ($line =~ /v=[\'\"](.*)[\'\"]/) ;

Fehler...

NEW REGEX ERROR reading osm file frankfurt0.osm, line follows (expecting
node or k/v for way):
   


NEW REGEX ERROR reading osm file frankfurt0.osm, line follows (expecting
node or k/v for way):
   


Komischerweise ist das das einzige, das nicht geht.

folgendes schafft keine abhilfe, im gegenteil:
my ($v) = ($line =~ /v=[\'\"]([.\d]*)[\'\"]/) ;


Dein "NEW REGEX ERROR" wird erzeugt mit
if($v) printf "NEW REGEX ERROR ..." (oder so ähnlich)?.

Verwenden musst Du
if(defined($v))

Die Werte "0", "" sind beide nicht wahr aber definiert.

Ciao
--
http://www.dstoecker.eu/ (PGP key available)___
Talk-de mailing list
Talk-de@openstreetmap.org
http://lists.openstreetmap.org/listinfo/talk-de


Re: [Talk-de] PERL REGEX?

2008-10-16 Diskussionsfäden [EMAIL PROTECTED]
es geht so nicht...

REGEX ist nun:

my ($v) = ($line =~ /v=[\'\"](.*)[\'\"]/) ;

Fehler...

NEW REGEX ERROR reading osm file frankfurt0.osm, line follows (expecting 
node or k/v for way):



NEW REGEX ERROR reading osm file frankfurt0.osm, line follows (expecting 
node or k/v for way):



Komischerweise ist das das einzige, das nicht geht.

folgendes schafft keine abhilfe, im gegenteil:
my ($v) = ($line =~ /v=[\'\"]([.\d]*)[\'\"]/) ;

Gruß

Gerhard


- Original Message - 
From: "Frederik Ramm" <[EMAIL PROTECTED]>
To: "Openstreetmap allgemeines in Deutsch" 
Sent: Wednesday, October 15, 2008 10:04 PM
Subject: Re: [Talk-de] PERL REGEX?


Hallo,

GS wrote:
> ich habe:
>
>  my ($v) = ($line =~ /^.+v=[\'\"]([\/-\w\d\s\.:,\(\)]+)[\'\"]/);
>
> Ich will aber einfach nur den Text zwischen den Anführungszeichen mit 
> allem
> drum und dran. Probleme gibt es mit den dt. Umlauten.
>
> (.+) läuft nicht, warum?

Was genau willst Du? Einfach nur den "value" ausschneiden? Warum dan
diese komplizierte Regel?

my ($v) = ($a =~ /v=['"](.*)['"]/);

Wobei dies nicht so ganz sauber ist mit den Anfuehrungszeichen, eher
muesste man

my ($x, $v) = ($a =~ /v=(['"])(.*)\1/);

schreiben, um einen Fall wie

v="Eiscafe D'Angelo"

richtig zu behandeln.

Bye
Frederik

-- 
Frederik Ramm  ##  eMail [EMAIL PROTECTED]  ##  N49°00'09" E008°23'33"

___
Talk-de mailing list
Talk-de@openstreetmap.org
http://lists.openstreetmap.org/listinfo/talk-de 


___
Talk-de mailing list
Talk-de@openstreetmap.org
http://lists.openstreetmap.org/listinfo/talk-de


Re: [Talk-de] PERL REGEX?

2008-10-16 Diskussionsfäden Dirk Stöcker

On Wed, 15 Oct 2008, Frederik Ramm wrote:


ich habe:

 my ($v) = ($line =~ /^.+v=[\'\"]([\/-\w\d\s\.:,\(\)]+)[\'\"]/);

Ich will aber einfach nur den Text zwischen den Anführungszeichen mit allem
drum und dran. Probleme gibt es mit den dt. Umlauten.

(.+) läuft nicht, warum?


Was genau willst Du? Einfach nur den "value" ausschneiden? Warum dan
diese komplizierte Regel?

my ($v) = ($a =~ /v=['"](.*)['"]/);

Wobei dies nicht so ganz sauber ist mit den Anfuehrungszeichen, eher
muesste man

my ($x, $v) = ($a =~ /v=(['"])(.*)\1/);

schreiben, um einen Fall wie

v="Eiscafe D'Angelo"

richtig zu behandeln.


Und auch das klappt nur bei einer Gruppe (also wenn garantiert v der 
letzte Parameter in der Zeile ist). Komplett richtig ist dann:


my (undef, $v) = ($a =~ /v=(['"])(.*?)\1/);

--> Beachte ".*?" statt ".*"
--> $x braucht auch keiner :-)

Ciao
--
http://www.dstoecker.eu/ (PGP key available)___
Talk-de mailing list
Talk-de@openstreetmap.org
http://lists.openstreetmap.org/listinfo/talk-de


Re: [Talk-de] PERL REGEX?

2008-10-15 Diskussionsfäden Frederik Ramm
Hallo,

GS wrote:
> ich habe:
> 
>  my ($v) = ($line =~ /^.+v=[\'\"]([\/-\w\d\s\.:,\(\)]+)[\'\"]/);
> 
> Ich will aber einfach nur den Text zwischen den Anführungszeichen mit allem 
> drum und dran. Probleme gibt es mit den dt. Umlauten.
> 
> (.+) läuft nicht, warum?

Was genau willst Du? Einfach nur den "value" ausschneiden? Warum dan 
diese komplizierte Regel?

my ($v) = ($a =~ /v=['"](.*)['"]/);

Wobei dies nicht so ganz sauber ist mit den Anfuehrungszeichen, eher 
muesste man

my ($x, $v) = ($a =~ /v=(['"])(.*)\1/);

schreiben, um einen Fall wie

v="Eiscafe D'Angelo"

richtig zu behandeln.

Bye
Frederik

-- 
Frederik Ramm  ##  eMail [EMAIL PROTECTED]  ##  N49°00'09" E008°23'33"

___
Talk-de mailing list
Talk-de@openstreetmap.org
http://lists.openstreetmap.org/listinfo/talk-de


Re: [Talk-de] PERL REGEX?

2008-10-15 Diskussionsfäden Tobias Wendorff
GS schrieb:
>  my ($v) = ($line =~ /^.+v=[\'\"]([\/-\w\d\s\.:,\(\)]+)[\'\"]/);
> 
> Ich will aber einfach nur den Text zwischen den Anführungszeichen mit allem 
> drum und dran. Probleme gibt es mit den dt. Umlauten.
> 
> (.+) läuft nicht, warum?

AFAIK verbrät REGEX viel zu viel Performance.

Ich gucke immer, nach dem ersten und dann nach dem nächsten
Anführungszeichen.

blah = "tag"
^   ^

Dann schneide ich das Mittelding aus.

___
Talk-de mailing list
Talk-de@openstreetmap.org
http://lists.openstreetmap.org/listinfo/talk-de