2008-10-13 10 views
54

Was ist die beste/effizienteste Möglichkeit, Text zwischen Klammern zu extrahieren? Angenommen, ich möchte die Zeichenfolge "text" aus der Zeichenfolge "Ignoriere alles außer diesem (Text)" möglichst effizient abrufen.PHP: Der beste Weg, um Text in Klammern zu extrahieren?

Bisher war die beste, die ich mit ist dies habe kommen:

$fullString = "ignore everything except this (text)"; 
$start = strpos('(', $fullString); 
$end = strlen($fullString) - strpos(')', $fullString); 

$shortString = substr($fullString, $start, $end); 

Gibt es einen besseren Weg, dies zu tun? Ich weiß, dass die Verwendung von Regex im Allgemeinen weniger effizient ist, aber wenn ich die Anzahl der Funktionsaufrufe nicht reduzieren kann, wäre dies vielleicht der beste Ansatz? Gedanken?

+0

Sie könnten ['s ($ fullString) -> zwischen (" (",")) '] finden (https://github.com/delight-im/PHP-Str/blob/8fd0c608d5496d43adaa899642c1cce047e076dc/src/ Str.php # L412) hilfreich, wie in [diese eigenständige Bibliothek] (https://github.com/delight-im/PHP-Str) gefunden. – caw

Antwort

96

ich würde nur eine Regex machen und es hinter mir lassen. es sei denn, Sie genügend Iterationen zu tun, dass es ein enormes Performance-Problem wird, dann ist es einfach leichte Code (und verstehen, wenn Sie darauf zurückblicken)

$text = 'ignore everything except this (text)'; 
preg_match('#\((.*?)\)#', $text, $match); 
print $match[1]; 
+0

Ist nicht *? redundant? – Dimitry

+0

Nein, es ist nicht:. passt nur ein einzelnes Zeichen. –

+1

nicht unbedingt,? ist ein faules Spiel. ohne es, eine Zeichenfolge wie 'ignoriere (alles) außer diesem (Text)', würde die Übereinstimmung am Ende 'alles' sein, außer dies (Text ' – Owen

10

Also, eigentlich ist der Code, den Sie geschrieben nicht: substr()'s Parameter sind $ string, $ start und $ length und strpos()'s Parameter sind $haystack, $needle. Leicht modifiziert:

$str = "ignore everything except this (text)"; 
$start = strpos($str, '('); 
$end = strpos($str, ')', $start + 1); 
$length = $end - $start; 
$result = substr($str, $start + 1, $length - 1);

Einige Feinheiten: Ich $start + 1 im Offset-Parameter, um PHP zu helfen verwendet, während die strpos() Suche auf der zweiten Klammer zu tun; Wir erhöhen $start Eins und reduzieren $length, um die Klammern aus der Übereinstimmung auszuschließen.

In diesem Code gibt es auch keine Fehlerüberprüfung: Sie müssen sicherstellen, dass $start und $end nicht === false sind, bevor Sie die substr ausführen.

Wie für die Verwendung strpos/substr gegenüber Regex; Leistungsmäßig wird dieser Code einen regulären Ausdruck übertreffen. Es ist ein wenig wortreich. Ich esse und atme strpos/substr, also stört mich das nicht allzu sehr, aber jemand anderes mag die Kompaktheit einer Regex bevorzugen.

4

einen regulären Ausdruck verwenden:

if(preg_match('!\(([^\)]+)\)!', $text, $match)) 
    $text = $match[1]; 
2

Dies ist ein Beispielcode gesamten Text zwischen extrahieren ‚[‘ und ‚]‘ und speichert sie 2 separaten Arrays (dh Text in Klammern in einem Array und Text außerhalb Klammern in einem anderen Array)

function extract_text($string) 
    { 
    $text_outside=array(); 
    $text_inside=array(); 
    $t=""; 
    for($i=0;$i<strlen($string);$i++) 
    { 
     if($string[$i]=='[') 
     { 
      $text_outside[]=$t; 
      $t=""; 
      $t1=""; 
      $i++; 
      while($string[$i]!=']') 
      { 
       $t1.=$string[$i]; 
       $i++; 
      } 
      $text_inside[] = $t1; 

     } 
     else { 
      if($string[$i]!=']') 
      $t.=$string[$i]; 
      else { 
       continue; 
      } 

     } 
    } 
    if($t!="") 
    $text_outside[]=$t; 

    var_dump($text_outside); 
    echo "\n\n"; 
    var_dump($text_inside); 
    } 

Ausgang: extract_text ("? hallo wie geht es dir"); produzieren:

array(1) { 
    [0]=> 
    string(18) "hello how are you?" 
} 

array(0) { 
} 

extract_text ("Hallo [http://www.google.com/test.mp3] Wie geht es Ihnen?"); erzeugt

array(2) { 
    [0]=> 
    string(6) "hello " 
    [1]=> 
    string(13) " how are you?" 
} 


array(1) { 
    [0]=> 
    string(30) "http://www.google.com/test.mp3" 
} 
+0

+1 aber wie das gleiche für [* und *] ? Weil [] vielleicht nur in HTML verwendet wird. – Mike

0

Diese Funktion kann nützlich sein.

public static function getStringBetween($str,$from,$to, $withFromAndTo = false) 
    { 
     $sub = substr($str, strpos($str,$from)+strlen($from),strlen($str)); 
     if ($withFromAndTo) 
     return $from . substr($sub,0, strrpos($sub,$to)) . $to; 
     else 
     return substr($sub,0, strrpos($sub,$to)); 
    } 
    $inputString = "ignore everything except this (text)"; 
    $outputString = getStringBetween($inputString, '(', ')')); 
    echo $outputString; 
    //output will be test 

    $outputString = getStringBetween($inputString, '(', ')', true)); 
    echo $outputString; 
    //output will be (test) 

strpos() => Dies wird verwendet, um die Position des ersten Auftretens in einer Zeichenfolge zu finden.

strrpos() => Dies wird verwendet, um die Position des ersten Auftretens in einer Zeichenfolge zu finden.