Problem bei RegularExpressions

Anfängerfragen zum Programmieren mit PureBasic.
Benutzeravatar
KeyKon
Beiträge: 1412
Registriert: 10.09.2004 20:51
Computerausstattung: Laptop: i5 2,8 Ghz, 16GB DDR3 RAM, GeForce 555GT 2GB VRAM
PC: i7 4,3 Ghz, 32GB DDR3 RAM, GeForce 680 GTX 4GB VRAM
Win10 x64 Home/Prof
PB 5.30 (64bit)
Wohnort: Ansbach
Kontaktdaten:

Problem bei RegularExpressions

Beitrag von KeyKon »

Ich hoffe jemand von euch kennt sich gut damit aus, ich verzweifle hier schier...
Folgendes Problem:
Ich will mittel RegExp sämtliche Links einer Site einlesen, ich hab aber echt keinen Ansatz wie ich das bewerkstelligen soll, bisher hat mir ein Rummwurschteln mit den normalen Stringfunktionen gereicht, aber da ich mein Prog etwas Allroundfähiger gestalten will wäre das mit RegExp (denke ich) viel einfacher...

Es sollen also aus einem Quelltext alle <a href="link.htm"> rausgefischt werden, allerdings is HTML in der gestaltung ja leider sehr frei es muss also auch mit soetwas klarkommen <a href = ein/link.php > oder sowas <a style='was weis ich' href = 'www.seite.de' target='muh'>

Naja, ich hoffe ihr wisst was ich mein, vll hat ja jemand sogar schon sowas in der Art in der Schublade...
Hier ein Code aus der Hilfe wo man (glaube ich) nurnoch die richtige RegExpression einsetzen muss:

Code: Alles auswählen

site$ = "<html><head></head><body><p>text<a href = 'www.link.de'>blalabla</a></p><br /><a href= relativer.link target=_blank>dicht</a><a href="+Chr(34)+"link/link/weiter.php"+Chr(34)+" style='kA'>Muuh</a></body></html>";GetClipboardText()

If CreateRegularExpression(0, "???")

  Dim Result$(0)
  
  a = ExtractRegularExpression(0, site$, result$())
  
  MessageRequester("Info", "Nb strings found: "+Str(a))
  
  For k=0 To a-1
    MessageRequester("Info", Result$(k))
  Next

Else
  MessageRequester("Error", RegularExpressionError())
EndIf
Ergebniss sollte dann sowas in der Art sein:
www.link.de
relativer.link
link/link/weiter.php
THX schonmal im voraus...
(\/) (°,,,°) (\/)
Kevin
Beiträge: 236
Registriert: 11.06.2007 12:55

Beitrag von Kevin »

ich habe es jetzt mal mit den string befehlen gemacht

Code: Alles auswählen

site$ = "<html><head></head><body><p>text<a href = 'www.link.de'>blalabla</a></p><br /><a href= relativer.link target=_blank>dicht</a><a href="+Chr(34)+"link/link/weiter.php"+Chr(34)+" style='kA'>Muuh</a></body></html>";GetClipboardText() 

pos=0
Repeat
 find = FindString(site$, "href", position)
 position = find + 1
  
  If find
   pos = FindString(site$, "=", position) + 1
   find = FindString(site$,">", pos)
   find$ = Trim(Mid(site$,pos,find-pos))

   pos = FindString(find$, "'", 0)
   posb = FindString(find$, Chr(34), 0)
   
   Debug find$+" <<<<< mit "+Chr(34)+" und ' "
   
     If pos And (pos<posb Or Not posb) : pos + 1
      find = FindString(find$, "'", pos+1)
      find$ = Mid(find$, pos, find-pos)
     EndIf
   
     If posb And (posb<pos Or Not pos) : posb + 1
      find = FindString(find$, Chr(34), posb+1)
      find$ = Mid(find$, posb, find-posb)
     EndIf
   
   Debug find$
  EndIf

Until Not find
Benutzeravatar
cxAlex
Beiträge: 2111
Registriert: 26.06.2008 10:42

Beitrag von cxAlex »

Hier noch eine Methode mit String-Parsen:

Code: Alles auswählen

site$ = "<html><head></head><body><p>text<a href = 'www.link.de'>blalabla</a></p><br /><a href= relativer.link target=_blank>dicht</a><a href=" + Chr(34) + "link/link/weiter.php" + Chr(34) + " style='kA'>Muuh</a></body></html>";GetClipboardText()

Define *Char.Character, tText$
*Char = @site$

While *Char\c
  If *Char\c = '<'
    *Char + SizeOf(Character)
    tText$ = ""
    While ((*Char\c< = 'z') And (*Char\c> = 'a')) Or ((*Char\c< = 'Z') And (*Char\c> = 'A'))
      tText$ + Chr(*Char\c)
      *Char + SizeOf(Character)
    Wend
    tText$ = LCase(tText$)
    If *Char\c<>'>'
      If tText$ = "a" ; Tag finden
        Repeat
          *Char + SizeOf(Character)
        Until ((*Char\c< = 'z') And (*Char\c> = 'a')) Or ((*Char\c< = 'Z') And (*Char\c> = 'A')) Or (*Char\c = '>') Or (Not *Char\c)
        If *Char\c And (*Char\c<>'>')
          tText$ = ""
          While ((*Char\c< = 'z') And (*Char\c> = 'a')) Or ((*Char\c< = 'Z') And (*Char\c> = 'A'))
            tText$ + Chr(*Char\c)
            *Char + SizeOf(Character)
          Wend
          tText$ = LCase(tText$)
          If tText$ = "href" ; Attribut finden
            Repeat
              *Char + SizeOf(Character)
            Until ((*Char\c< = 'z') And (*Char\c> = 'a')) Or ((*Char\c< = 'Z') And (*Char\c> = 'A')) Or (*Char\c = 39) Or (*Char\c = '"') Or (*Char\c = '>') Or (Not *Char\c)
            tText$ = ""
            
            ; Link filtern
            If *Char\c = 39
              *Char + SizeOf(Character)
              While (*Char\c<>39) And *Char\c
                tText$ + Chr(*Char\c)
                *Char + SizeOf(Character)
              Wend

              Debug tText$
              
            ElseIf *Char\c = '"'
              *Char + SizeOf(Character)
              While (*Char\c<>'"') And *Char\c
                tText$ + Chr(*Char\c)
                *Char + SizeOf(Character)
              Wend
              Debug tText$
              
            ElseIf *Char\c And (*Char\c<>'>')

              While ((*Char\c< = '9') And (*Char\c> = '0')) Or ((*Char\c< = 'z') And (*Char\c> = 'a')) Or ((*Char\c< = 'Z') And (*Char\c> = 'A')) Or (*Char\c = '.') Or (*Char\c = '/') Or (*Char\c = '\')
                tText$ + Chr(*Char\c)
                *Char + SizeOf(Character)
              Wend
              
              Debug tText$
            EndIf
          EndIf
        EndIf
      EndIf
    EndIf
  EndIf
  *Char + SizeOf(Character)
Wend
Projekte: IO.pbi, vcpu
Pausierte Projekte: Easy Network Manager, µC Emulator
Aufgegebene Projekte: ECluster

Bild

PB 5.1 x64/x86; OS: Win7 x64/Ubuntu 10.x x86
Benutzeravatar
DrShrek
Beiträge: 1970
Registriert: 08.09.2004 00:59

Beitrag von DrShrek »

Hier eine erste Variante mit RegEx (Unvollständig!):

Code: Alles auswählen

site$ = "<html><head></head><body><p>text<a href = 'www.link.de'>blalabla</a></p><br /><a href= relativer.link target=_blank>dicht</a><a href="+Chr(34)+"link/link/weiter.php"+Chr(34)+" style='kA'>Muuh</a></body></html>";GetClipboardText() 

If CreateRegularExpression(0, "href.*?=*>")
  Dim Result$(0)
  NbFound = ExtractRegularExpression(0, site$, Result$())
  For k = 0 To NbFound-1
    Debug Result$(k) 
  Next
Else
  Debug RegularExpressionError()
EndIf
Siehste! Geht doch....?!
PB*, *4PB, PetriDish, Movie2Image, PictureManager, TrainYourBrain, ...
Benutzeravatar
KeyKon
Beiträge: 1412
Registriert: 10.09.2004 20:51
Computerausstattung: Laptop: i5 2,8 Ghz, 16GB DDR3 RAM, GeForce 555GT 2GB VRAM
PC: i7 4,3 Ghz, 32GB DDR3 RAM, GeForce 680 GTX 4GB VRAM
Win10 x64 Home/Prof
PB 5.30 (64bit)
Wohnort: Ansbach
Kontaktdaten:

Beitrag von KeyKon »

Mh, cxAlex Lösung Funktioniert gut und schnell...
Nur Zahlen im Link scheinst du nicht zu berücksichtigen, aber das ist ja leicht zu Ergänzen ( Or ((*Char\c< = '9') And (*Char\c> = '0')))...
(\/) (°,,,°) (\/)
Benutzeravatar
.:M:.
Beiträge: 44
Registriert: 29.07.2008 04:12

Beitrag von .:M:. »

Ich will auch mitmachen :twisted:

Code: Alles auswählen

site$ = "<html><head></head><body><p>text<a href = 'www.link.de'>blalabla</a></p><br /><a href= relativer.link target=_blank>dicht</a><a href="+Chr(34)+"link/link/weiter.php"+Chr(34)+" style='kA'>Muuh</a></body></html>";GetClipboardText() 

For i=1 To CountString(site$,"<")+1
  link$=StringField(site$, i, "<")
  If FindString(link$, "href", 1)
    link$=StringField(link$, 2, "=")
    link$=StringField(link$, 1, ">")
    link$=Trim(link$) 
    If FindString(link$, " ", 1)
      link$=StringField(link$, 1, " ")
    EndIf  
    Debug link$
  EndIf   
Next i
PB 5.11 Beta1 32Bit | Win 7 Pro 64Bit
Benutzeravatar
Thalius
Beiträge: 476
Registriert: 17.02.2005 16:17
Wohnort: Basel / Schweiz

Beitrag von Thalius »

"...smoking hash-tables until until you run out of memory." :P
Benutzeravatar
edel
Beiträge: 3667
Registriert: 28.07.2005 12:39
Computerausstattung: GameBoy
Kontaktdaten:

Beitrag von edel »

OT:
Na der Thread war lustig, ein offensichtlichen Fehler im Regexp Ausdruck und
es dann auf die Lib schieben... Aber nochmal an IceSoft, das einzige was
verbugt ist oder war, ist die PB Lib selber. Die Regex Lib mag vielleicht auch
ihre Fehler haben, aber solch einen Bug hast du sicherlich noch nicht
gefunden. Also kein Grund hier nach einem Update zu schreien..
Benutzeravatar
DrShrek
Beiträge: 1970
Registriert: 08.09.2004 00:59

Beitrag von DrShrek »

edel hat geschrieben:Also kein Grund hier nach einem Update zu schreien..
Doch. Das die Lib die bei PB mitgeliefert wird von 2007 ist, ist schon Grund genug.
Siehste! Geht doch....?!
PB*, *4PB, PetriDish, Movie2Image, PictureManager, TrainYourBrain, ...
Benutzeravatar
mk-soft
Beiträge: 3855
Registriert: 24.11.2004 13:12
Wohnort: Germany

Beitrag von mk-soft »

Quelle http://expat.sourceforge.net/
News

5 June 2007, Expat 2.0.1 released.

Release 2.0.1 of the Expat XML parser is a bugfix release resolving both code and build related issues. Changes include:
Alles ist möglich, fragt sich nur wie...
Projekte ThreadToGUI / EventDesigner V3 / OOP-BaseClass-Modul
Downloads auf MyWebspace / OneDrive
Antworten