login  Naam:   Wachtwoord: 
Registreer je!
 Forum

preg_replace om alleen links over te houden

Offline GroundZero - 26/10/2011 16:47
Avatar van GroundZeroLid Beste,

ik wil voor een partner website van ons alle links ophalen van hun site. Ik heb met onderstaand script hun site opgehaald echter wil ik nu ALLES verwijderen behalven de links.

Ik heb gekeken naar de regex expressies maar ik begrijp er helaas weinig van, vind het erg moeilijk.

Zou iemand mij wat uitleg kunnen geven over hoe ik kan realiseren wat ik graag wil?

Dus ik wil enkel overhouden in een array:

<a href=".....">....</a>

Waarbij de puntjes een willekeurig iets is dus.

  1. $ch = curl_init();
  2. curl_setopt($ch, CURLOPT_URL, 'http://www.hema.nl/');
  3. curl_setopt ($ch, CURLOPT_USERAGENT, "Mozilla/4.0 (compatible; MSIE 5.01; Windows NT 5.0)");
  4. curl_setopt($ch, CURLOPT_HTTPHEADER, array('Accept-Language: en-us,en;q=0.5'));
  5. curl_setopt ($ch, CURLOPT_RETURNTRANSFER, 1);
  6. $result = curl_exec($ch);
  7. curl_close($ch);
  8.  
  9. $data = $result;

6 antwoorden

Gesponsorde links
Offline vinTage - 26/10/2011 20:24
Avatar van vinTage Nieuw lid
  1. <?php
  2. $site = file_get_contents("http://www.hema.nl");
  3. preg_match_all("~<a href=(.*)\>(.*)<\/a>~i", $site, $matches);
  4. ?>
  5. <pre>
  6. <?php
  7. print_r($matches);
  8. ?>
  9. </pre>
Offline GroundZero - 26/10/2011 20:28
Avatar van GroundZero Lid Super dankjewel vinTage!

Ik heb nu dit:

  1. <?php
  2. $ch = curl_init();
  3. curl_setopt($ch, CURLOPT_URL, 'http://www.mijnsite.nl/');
  4. curl_setopt ($ch, CURLOPT_USERAGENT, "Mozilla/4.0 (compatible; MSIE 5.01; Windows NT 5.0)");
  5. curl_setopt($ch, CURLOPT_HTTPHEADER, array('Accept-Language: en-us,en;q=0.5'));
  6. curl_setopt ($ch, CURLOPT_RETURNTRANSFER, 1);
  7. $result = curl_exec($ch);
  8. curl_close($ch);
  9.  
  10. // lijsten instellen
  11. $lijst = array(); // lijst om alle gevonde links in op te slaan
  12.  
  13. if( $result )
  14. {
  15. /*
  16. alle links zoeken en in de array output plaatsen in volgorde van
  17. de PREG_SET_ORDER functie
  18. */
  19. preg_match_all( '/<a(?:[^>]*)href=\"([^\"]*)\"(?:[^>]*)>(?:[^<]*)<\/a>/is', $result, $output, PREG_SET_ORDER );
  20.  
  21. /*
  22. Door een loop halen om te kijken of http er voor staat, zo niet dan
  23. ervoor plaatsen omdat we hele links nodig hebben!
  24. */
  25. foreach($output as $value)
  26. {
  27. if(!preg_match("/http/i", $value[1]))
  28. {
  29. $lijst[] = 'http://www.mijnsite.nl'.$value[1];
  30. }
  31. else
  32. {
  33. $lijst[] = $value[1];
  34. }
  35. }
  36.  
  37. // weergeven
  38. foreach($lijst as $value)
  39. {
  40. echo $value.'<br />';
  41. }
  42. }
  43. ?>



werkt prima echter wil ik enkel de LINK overhouden dus "http://www....nl" zeg maar... hoe kan ik nu de rest weg strippen?

Ik heb nu


<a href="....">...</a>
Offline vinTage - 26/10/2011 20:33 (laatste wijziging 26/10/2011 20:35)
Avatar van vinTage Nieuw lid strip_tags($value);

of

str_replace('wat je weg wilt', '', $value);
Offline Martijn - 03/11/2011 18:33 (laatste wijziging 03/11/2011 18:36)
Avatar van Martijn Crew PHP of gewoon $values[0]. T is namelijk je eerste group ( (.*?) ) dus je hebt allang  dat van de str_replace kan ook, maar als de url dan wisselt, werkt de regex niet meer 

Mijn suggestie gebaseerd op die van vintage:

#<a(?:.*?)href=\"(.*?)\"(?:.*?)>(?:.*?)<\/a>#si

die lijkt veel enger, maar t valt super mee, zal m stap voor sta uitleggen:
- De # doet hetzelfde als de ~ van vintage, in dit voorbeeld even mijn voorkeur omdat ik ~ nooit gebruik en het effect niet weet
- De SI op het einde is Singleline en case Insensative
- Alle groups die ik niet relevant vindt geeft ik '?:'. Betekent dat ie de match dus niet opslaat, maar dat daar wel alles kan staan, dit omdat:

- Na de <a staat váák de href, maar als iemand de url net anders maakt, werkt dat niet meer (<a class="iets" href="">). Door de selector hier mag ALLES tussen de 'a' en 'href' staan, en door de ?: onthoudt ie dat niet.
- Dan de href, die willen we wel dus geen ?: ervoor
- Daarna weer 1 met ?: erna, voor het geval iemand de url weer anders maakt (<a href="" class="iets">)
- Dan een group voor de waarde van de anchor (dus wat de user ziet). Door de ?: wordt het weer niet onthouden, weghalen als je het wel wilt
- en dan op t einde een mooie </a>


Hoe groot is de kans dat de url niet zo is: <a href="url">tekst</a>? Zeer aannemelijk. Als je op SEO niveau bezig bent, ga je de title aan een anchor geven (<a href="" title="Als je je muis stilhoudt zie je dit!">) en dan werkt het al niet meer. Bovendien als er ergens 2 spaties staan, werkt het nog. Als iemand iets mafs doet, werkt het nog 

^ Beetje lang, maar wel handig om even te lezen
Offline WouterJ - 03/11/2011 20:40 (laatste wijziging 03/11/2011 20:41)
Avatar van WouterJ HTML gevorderde @Martijn,
> De # doet hetzelfde als de ~ van vintage, in dit voorbeeld even mijn voorkeur omdat ik ~ nooit gebruik en het effect niet weet
Dit is precies hetzelfde, hetgeen het meest voorkomt is //. Dit omdat dit in JavaScript ook zo werkt, alleen PHP moet weer een quote eromheen hebben omdat ze het type regex niet kennen.

>Alle groups die ik niet relevant vindt geeft ik '?:'. Betekent dat ie de match dus niet opslaat, maar dat daar wel alles kan staan, dit omdat:
Dit vind ik er behoorlijk onoverzichtelijk uitzien. Je kan veel beter gewoon de group dan weg laten.
Ook zou ik nog global er bij toevoegen als flag, zo kun je meerdere links ophalen:
/<a\s.*?href=('|")(.*?)(?:'|").*?>.*?</a>/gi
voorbeeld
(deze is ook nog zo dat het niet uitmaakt of je "" of '' gebruikt in de href, nog beter voor gekke codes).
Offline Martijn - 04/11/2011 14:05
Avatar van Martijn Crew PHP Die is inderdaad weer een stukje overzichtelijker, al mist je eerst ('|") de ?":)
Gesponsorde links
Je moet ingelogd zijn om een reactie te kunnen posten.
Actieve forumberichten
© 2002-2024 Sitemasters.be - Regels - Laadtijd: 0.225s