Ich hoffe, dass diese Frage kein RTFM ist.
Ich versuche ein Python-Skript zu schreiben, das Links von einer Standard-HTML-Webseite extrahiert (die <link href...
-Tags).
Ich habe im Internet nach übereinstimmenden Regexen gesucht und viele verschiedene Muster gefunden. Gibt es einen vereinbarten Standard-Regex, der zu Links passt?
Adam
UPDATE: Ich suche eigentlich nach zwei verschiedenen Antworten:
Igal Serban
und cletus
!) Wie andere vorgeschlagen haben, ist BeautifulSoup eine gute Lösung, wenn keine Echtzeit-ähnliche Leistung erforderlich ist:
%Vor%Wie für die zweite Frage, ja, HTML-Links sollten gut definiert sein, aber die HTML, die Sie tatsächlich begegnen, ist sehr unwahrscheinlich, Standard zu sein. Das Schöne an BeautifulSoup ist, dass es browserähnliche Heuristiken verwendet, um zu versuchen, das nicht standardmäßige, fehlerhafte HTML zu analysieren, auf das Sie wahrscheinlich stoßen werden.
Wenn Sie sicher sind, dass Sie an Standard-XHTML arbeiten, können Sie (viel) schnellere XML-Parser wie Expat verwenden.
Regex wird aus den oben genannten Gründen (der Parser muss den Status beibehalten, und Regex kann das nicht tun) niemals eine allgemeine Lösung sein.
Nein, gibt es nicht.
Sie können Beautiful Soup in Erwägung ziehen. Sie können es den Standard zum Analysieren von HTML-Dateien nennen.
Sollte ein Link keine wohldefinierte Regex sein?
Nein, [X] HTML ist im allgemeinen Fall nicht mit regex analysierbar. Betrachten Sie Beispiele wie:
%Vor%und das sind nur ein paar zufällige gültige Beispiele; Wenn Sie HTML-Code aus der realen Welt verarbeiten müssen, gibt es eine Million falsch gestalteter Möglichkeiten.
Wenn Sie das genaue Ausgabeformat der Zielseite kennen und sich darauf verlassen können, können Sie mit regex fortfahren. Ansonsten ist es völlig falsch, Webseiten zu scrappen.
Sollte ein Link keine klar definierte Regex sein? Dies ist eine eher theoretische Frage,
Ich habe die zweite Antwort von PEZ:
Ich glaube nicht, dass HTML sich für "gut definierte" reguläre Ausdrücke eignet, da es keine reguläre Sprache ist.
Soweit ich weiß, kann jedes HTML-Tag eine beliebige Anzahl von verschachtelten Tags enthalten. Zum Beispiel:
%Vor%Um also ein Tag korrekt abzugleichen, müssen Sie in der Lage sein, mindestens Strings des Formulars zu finden:
%Vor%wobei B den Anfang eines Tags und E das Ende bedeutet. Das heißt, Sie müssen in der Lage sein, Strings zu bilden, die durch eine beliebige Anzahl von Bs gebildet werden, gefolgt von der gleichen Anzahl von E's. Um dies zu tun, muss Ihr Matcher "zählen" können, und reguläre Ausdrücke (d. H. Endliche Automaten) können das einfach nicht (um zu zählen, benötigt ein Automat mindestens einen Stapel). Bezugnehmend auf die Antwort von PEZ ist HTML eine kontextfreie Grammatik, keine reguläre Sprache.
Beantworte deine zwei Teilfragen dort.
Als Antwort auf Frage 2 (sollte kein Link ein gut definierter regulärer Ausdruck sein) ist die Antwort ... nein.
Eine HTML-Link-Struktur ist rekursiv, ähnlich wie Parens und Klammern in Programmiersprachen. Es muss eine gleiche Anzahl von Start- und Endkonstrukten geben und der Ausdruck "link" kann in sich selbst verschachtelt sein.
Um einen "Link" -Ausdruck korrekt zu finden, wäre ein Regex erforderlich, um die Start- und End-Tags zu zählen. Reguläre Ausdrücke sind eine Klasse von Finite Automaten. Definitionsgemäß kann ein finite Automat keine Konstrukte innerhalb eines Musters "zählen". Eine Grammatik ist erforderlich, um eine solche rekursive Datenstruktur zu beschreiben. Die Unfähigkeit einer Regex zu "zählen" ist der Grund, warum Sie Programmiersprachen sehen, die mit Grammatiken im Gegensatz zu regulären Ausdrücken beschrieben werden.
Es ist also nicht möglich, eine Regex zu erstellen, die genau 100% aller "Link" -Ausdrücke entspricht. Es gibt sicherlich Regex, die eine Menge von "Link" mit einem hohen Maß an Genauigkeit übereinstimmen, aber sie werden niemals perfekt sein.
Ich habe kürzlich einen Artikel über dieses Problem geschrieben. Einschränkungen des regulären Ausdrucks