2012-03-29 2 views
0

So habe ich die folgende XML-Kette:Überprüfen Sie, ob XML-Kette Exists in PHP

$xml->assessment->outcomes_processing->outcomes->decvar->attributes()->cutvalue 

XML-Beispiel In einigen XML-Dateien xml- $> Assessment-> outcomes_processing-> outcomes-> .. . existiert. Aber hier gibt es nur $ xml-> assessment.

<questestinterop> 
    <assessment ident="nedolat78356769204914" title="welkom woordenschat 4"> 
    <qtimetadata> 
     <qtimetadatafield> 
     <fieldlabel>qmd_assessmenttype</fieldlabel> 
     <fieldentry>Assessment</fieldentry> 
     </qtimetadatafield> 
    </qtimetadata> 
    <section ident="nedolat78356769204915" title="Woordenschat"> 
     <selection_ordering> 
     <selection/> 
     <order order_type="Sequential"/> 
     </selection_ordering> 
     <item ident="QTIEDIT:FIB:34932158" title="Oefening 1"> 
     ... 
     </item> 
    </section> 
    </assessment> 
</questestinterop> 

Im Moment bekomme ich den Fehler: "Versuch, die Eigenschaft von Nicht-Objekt zu bekommen". Was ist Logik, weil der Knoten von Ergebnisse nicht existiert.

Also habe ich eine Lösung mit isset() versucht, die offensichtlich auch nicht funktioniert.

isset($xml->assessment->outcomes_processing->outcomes->decvar->attributes()->cutvalue) ? ... : null 

Das gibt mir den gleichen Fehler. Da der Knoten Ergebnisse nicht existiert, so wirft er mir den Fehler sofort. Die Lösung könnte sein, jeden Knoten einzeln mit isset() zu prüfen, natürlich mit einer Funktion, da ich sonst viel zu tun habe ...

Das ist meine Funktion, die funktioniert nicht, weil die Zeichenfolge ' ->‘kann nicht als pHP-Code verarbeitet werden:

// xml: xml structure form SimpleXML 
// chain: assessment->outcomes_processing->outcomes->decvar->attributes()->cutvalue 
function checkIfXMLChainExists($xml, $chain) { 
    $xmlChain = ''; 
    $i = 0; 
    $nodes = explode('->', $chain); 
    $numItems = count($nodes); 

    // experimenting with eval() to treat '->' as ->; failed to work 
    $a = '$xml->assessment->outcomes_processing'; 
    $t = eval($a); 
    echo $t; 
    print_r($t); 

    foreach ($nodes as $node) { 
    $xmlChain .= '->' . $node; 

    if (isset($xml->$xmlChain)) { // Node exists 
     if ($i+1 == $numItems) { 
     return $xml->$xmlChain; 
     } 
    } else { // Node does not exists 
     return 'does not exist'; 
    } 
    $i++; 
    } 

hat jemand ein paar Ideen hat, weil ich im Moment jede Inspiration habe nicht :(

Vielen Dank im Voraus

+0

Wie wäre es mit Xpath ?? : P – pleasedontbelong

+0

Hängt von Ihrem XML ab. Können wir eine Probe sehen? Je nach Struktur müssen Sie beispielsweise etwas wie $ xml-> assessment [0] -> outcomes_processing machen. – halfer

+0

Es wäre besser, über '$ xml-> children()' zu iterieren, anstatt 'eval', btw zu verwenden. – halfer

Antwort

1

die Datenkosten referenziert durch die Kette oder NULL wenn es nicht existiert.

function getDataIfExists() { 

    // We accept an unknown number of arguments 
    $args = func_get_args(); 

    if (!count($args)) { 
    trigger_error('getDataIfExists() expects a minimum of 1 argument', E_USER_WARNING); 
    return NULL; 
    } 

    // The object we are working with 
    $baseObj = array_shift($args); 

    // Check it actually is an object 
    if (!is_object($baseObj)) { 
    trigger_error('getDataIfExists(): first argument must be an object', E_USER_WARNING); 
    return NULL; 
    } 

    // Loop subsequent arguments, check they are valid and get their value(s) 
    foreach ($args as $arg) { 
    $arg = (string) $arg; 
    if (substr($arg, -2) == '()') { // method 
     $arg = substr($arg, 0, -2); 
     if (!method_exists($baseObj, $arg)) return NULL; 
     $baseObj = $baseObj->$arg(); 
    } else { // property 
     if (!isset($baseObj->$arg)) return NULL; 
     $baseObj = $baseObj->$arg; 
    } 
    } 

    // If we get here $baseObj will contain the item referenced by the supplied chain 
    return $baseObj; 

} 

// Call it like this: 
$subObj = getDataIfExists($xml, 'assessment', 'outcomes_processing', 'outcomes', 'decvar', 'attributes()', 'cutvalue'); 
+0

Wow eigentlich so einfach, aber ich wäre nie dazu gekommen. Danke Kamerad! –

Verwandte Themen