3

Xml

<CRates>
    <Currencies>
        <Currency>
            <ID>AED</ID>
            <Units>1</Units>
            <Rate>0.17200000</Rate>
        </Currency>
        <Currency>
            <ID>ATS</ID>
            <Units>1</Units>
            <Rate>0.04102750</Rate>
        </Currency>
    </Currencies>
</CRates>

Want to get for example Rate value where ID is ATS

At the moment can get only in such way

$xmlDoc = simplexml_load_file('__joomla.xml');
echo $xmlDoc->Currencies->Currency[1]->Rate;

<ID>ATS</ID> is within the second <Currency>, so Currency[1]

Of course echo $xmlDoc->Currencies->Currency[ATS]->Rate; does not work. But is any simple way to get it work?

Seems need to use foreach and inside foreach if <ID> == ATS, echo <Rate>

3
  • I think you can find this link helpful php.net/manual/en/simplexmliterator.getchildren.php Commented Aug 1, 2013 at 19:10
  • i am confused, what do you want to do? Pull all the Rate values? Only for a specific ID? Commented Aug 1, 2013 at 19:14
  • Only specific <Rate> of <Currency> where <ID> matches set condition. For example, user wants to see Rate for currency ATS. So need to show the Rate only for currency ATS Commented Aug 1, 2013 at 19:16

2 Answers 2

3

Try this:

// This way should work for all versions of PHP
$rate = false;
foreach ($xmlDoc->Currencies->Currency as $currency)
{
    if ((string)$currency->ID == 'ATS')
    {
        $rate = (string)$currency->Rate;
        break;
    }
}

// This way should work for newer versions of PHP only, I personally think that anonymous functions like this add to the readability which is why I included both options
$rate = call_user_func(function() use ($xmlDoc) {
    foreach ($xmlDoc->Currencies->Currency as $currency)
    {
        if ((string)$currency->ID == 'ATS')
            return (string)$currency->Rate;
    }
    return false;
});

// Using false to signify failure is the standard in PHP
if ($rate !== false)
    echo 'The rate is: ',$rate;
else
    echo 'Rate not found';

You may not need to cast to string but I believe if you don't you'll end up with SimpleXMLElement objects (or something with a similar name) rather than strings.

Sign up to request clarification or add additional context in comments.

4 Comments

+1 but I would use if(!empty($rate)) instead of if($rate != false) in case the rate approaches 0 for any reason. also, you have an extra trailing = in that final if statement..
@XaxD - Returning false when something fails is the standard in PHP. Most functions already act that way and many are being changed towards that model. Not a typo "!==" rather than just "!=" will ensure it is false AND of the same type so "-1" won't be treated as a miss.
@XaxD - echo takes infinite parameters so comma is preferred to period as it will echo them both individually rather than concatenating first.
@XaxD - np, both things are actually common oversights. I'd actually encourage you to leave the comments as it may help others.
0

Perhaps using xpath, something like:

$xmlDoc = simplexml_load_file('__joomla.xml'); 
// find all currency records with code value of ATS
$result = $xmlDoc->xpath("Currencies/Currency/ID[.='ATS']/parent::*");  
print_r($result); 

gives

Array
(
    [0] => SimpleXMLElement Object
        (
            [ID] => ATS
            [Units] => 1
            [Rate] => 0.04102750
        )

)

while

$xmlDoc = simplexml_load_file('__joomla.xml'); 
print_r($xmlDoc); 
// find all currency records with code value of ATS
$rate = $xmlDoc->xpath("Currencies/Currency/ID[.='ATS']/parent::*"); 
print_r((float) $rate[0]->Rate); 

gives

0.0410275

3 Comments

In output get Array ( )
@user2465936 - I may be wrong but I believe print_r doesn't work properly with SimpleXML. Unsure why but I've used it a bunch and my brain is having incomplete flashbacks.
Modified for case-sensitivity, and use of ID rather than code

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.