2009-09-18 14 views
18

Jaki jest najlepszy sposób na uzyskanie treści między dwoma ciągami znaków, np.Pobierz treść między dwoma ciągami PHP

ob_start(); 
include('externalfile.html'); ## see below 
$out = ob_get_contents(); 
ob_end_clean(); 

preg_match('/{FINDME}(.|\n*)+{\/FINDME}/',$out,$matches); 
$match = $matches[0]; 

echo $match; 

## I have used .|\n* as it needs to check for new lines. Is this correct? 

## externalfile.html 

{FINDME} 
Text Here 
{/FINDME} 

Z jakiegoś powodu wydaje się, że działa na jednym miejscu w moim kodzie, a nie innym. Czy robię to w odpowiedni sposób? Czy jest jakiś lepszy sposób?

Również jest bufor wyjściowy sposób to zrobić lub file_get_contents?

Z góry dziękuję!

+0

Jeśli działa w niektórych sytuacjach, a nie innych, należy podać przykłady, kiedy działa, a kiedy nie. – Welbog

Odpowiedz

35
  • Użyj # zamiast , więc nie musisz ich uciec.
  • The powoduje również, że zawierają nowe linie.
  • { i } ma różne funkcje, takie jak od n do m razy w {n,m}.
  • Podstawowym

    preg_match('#\\{FINDME\\}(.+)\\{/FINDME\\}#s',$out,$matches); 
    
  • Zaawansowana różnych znaczników itp (stylizacja nie jest tak miło przez javascript).

    $delimiter = '#'; 
    $startTag = '{FINDME}'; 
    $endTag = '{/FINDME}'; 
    $regex = $delimiter . preg_quote($startTag, $delimiter) 
            . '(.*?)' 
            . preg_quote($endTag, $delimiter) 
            . $delimiter 
            . 's'; 
    preg_match($regex,$out,$matches); 
    

Umieść ten kod w funkcji

  • Dla każdego pliku, który nie chce execue żadnego bezpański kodu php, należy użyć file_get_contents. include/require nie powinno być tam nawet opcją.
+2

Założę się, że {FINDME} jest po prostu dla ilustracji –

39

Możesz równie dobrze użyć substr i strpos do tego.

$startsAt = strpos($out, "{FINDME}") + strlen("{FINDME}"); 
$endsAt = strpos($out, "{/FINDME}", $startsAt); 
$result = substr($out, $startsAt, $endsAt - $startsAt); 

Musisz dodać kontrolę błędów, aby obsłużyć przypadek, w którym nie znajduje się FINDME.

+1

To jest najlepszy sposób, aby to zrobić, gdy jest to możliwe –

+0

zgadzam się z Cem Kalyoncu – Peter

+0

Dziękuję za alternatywne rozwiązanie, rozwiązał mój problem. Wykonałem preg_match z dużym ciągiem, który zwrócił pustą tablicę. Twoje rozwiązanie naprawiło mój problem. – meenxo

1

Podziały linii mogą powodować problemy w RegEx, spróbuj usunąć lub zastąpić je \ n przed przetwarzaniem.

-1

Szybki sposób na umieszczenie wszystkiego w jednym ciągu.

$newlines = array("\t","\n","\r","\x20\x20","\0","\x0B"); 
$one_string = str_replace($newlines, "", html_entity_decode($content)); 
0
function getInbetweenStrings($start, $end, $str){ 
    $matches = array(); 
    $regex = "/$start([a-zA-Z0-9_]*)$end/"; 
    preg_match_all($regex, $str, $matches); 
    return $matches[1]; 
} 


$str = "C://@@[email protected]@/@@[email protected]@/@@[email protected]@"; 
$str_arr = getInbetweenStrings('@@', '@@', $str); 

print_r($str_arr); 
+0

To po prostu nie działa. na przykład 'getInbetweenStrings ('start', 'end', 'start get this string end');' – billynoah

4

Kocham te dwa rozwiązania

function GetBetween($content,$start,$end) 
{ 
    $r = explode($start, $content); 
    if (isset($r[1])){ 
     $r = explode($end, $r[1]); 
     return $r[0]; 
    } 
    return ''; 
} 


function get_string_between($string, $start, $end){ 
    $string = " ".$string; 
    $ini = strpos($string,$start); 
    if ($ini == 0) return ""; 
    $ini += strlen($start); 
    $len = strpos($string,$end,$ini) - $ini; 
    return substr($string,$ini,$len); 
} 

Ja również kilka punktów odniesienia, jak również z obu rozwiązań i oba powyższe dają prawie taki sam czas. Możesz to również przetestować. Dałem obu funkcjom plik do odczytania, który zawierał około 60000 znaków (sprawdzony przy pomocy liczby słów Worda), a obie funkcje zaowocowały znalezieniem około 0,000999 sekund.

$startTime = microtime(true); 
GetBetween($str, '<start>', '<end>'); 
echo "Explodin Function took: ".(microtime(true) - $startTime) . " to finish<br />"; 

$startTime = microtime(true); 
get_string_between($str, '<start>', '<end>'); 
echo "Subsring Function took: ".(microtime(true) - $startTime) . " to finish<br />"; 
+0

To jest świetne. Czy można go użyć, aby znaleźć wiele dopasowań? Więc zwróć tablicę ze wszystkimi dopasowaniami? –

0

To jest rozwiązanie PHP, które zwraca ciągi znalezione między tagami w stogu siana. Działa, ale nie testowałem wydajności. Potrzebowałem tego i zostałem zainspirowany odpowiedzią Adama Wrighta na tej stronie.

Zwraca tablicę() zawierającą wszystkie łańcuchy znalezione między znacznikiem $ a znacznikiem $ end_symbold. $ Znacznik w stogu siana lub FALSE, jeśli nie znaleziono znacznika $ end_symbol. $, Ponieważ nie ma pary znaczników w stadzie $ haystack.

function str_between_tags($haystack, $tag, $end_symbol){ 
    $c_end_tags = substr_count($haystack, $end_symbol.$tag); 
    if(!$c_end_tags) return FALSE; 

    for($i=0; $i<$c_end_tags; $i++){ 
     $p_s = strpos($haystack, $tag, (($p_e)?$p_e+strlen($end_symbol.$tag):NULL)) + strlen($tag); 
     $p_e = strpos($haystack, $end_symbol.$tag, $p_s); 
     $result[] = substr($haystack, $p_s, $p_e - $p_s); 
    } 
    return $result; 
} 
Powiązane problemy