4

I have a function xml2array that parses my xml file to an Array. Now when I have an empty value in my xml file the function converts this to array( ) an empty array.

So < test >< /test > becomes [test]=>array(), but I want that to be an empty string "".

Does anybody know how to edit my function below:

<?php
    function xml2array($contents, $get_attributes = 1, $priority = 'tag') {

    $parser = xml_parser_create('');
    xml_parser_set_option($parser, XML_OPTION_TARGET_ENCODING, "UTF-8");
    xml_parser_set_option($parser, XML_OPTION_CASE_FOLDING, 0);
    xml_parser_set_option($parser, XML_OPTION_SKIP_WHITE, 1);
    xml_parse_into_struct($parser, trim($contents), $xml_values);
    xml_parser_free($parser);
    if (!$xml_values)
        return; //Hmm...
    $xml_array = array ();
    $parents = array ();
    $opened_tags = array ();
    $arr = array ();
    $current = & $xml_array;
    $repeated_tag_index = array (); 
    foreach ($xml_values as $data)
    {
        unset ($attributes, $value);
        extract($data);
        $result = array ();
        $attributes_data = array ();
        if (isset ($value))
        {
            if ($priority == 'tag')
                $result = $value;
            else
                $result['value'] = $value;
        }
        if (isset ($attributes) and $get_attributes)
        {
            foreach ($attributes as $attr => $val)
            {
                if($attr == 'xsi:type') continue;
                if($attr == 'xsi:nil') continue;

                if ($priority == 'tag')
                    $attributes_data[$attr] = $val;
                else
                    $result['attr'][$attr] = $val; //Set all the attributes in a array called 'attr'
            }
        }
        if ($type == "open")
        { 
            $parent[$level -1] = & $current;
            if (!is_array($current) or (!in_array($tag, array_keys($current))))
            {
                $current[$tag] = $result;
                if ($attributes_data)
                    $current[$tag . '_attr'] = $attributes_data;
                $repeated_tag_index[$tag . '_' . $level] = 1;
                $current = & $current[$tag];
            }
            else
            {
                if (isset ($current[$tag][0]))
                {
                    $current[$tag][$repeated_tag_index[$tag . '_' . $level]] = $result;
                    $repeated_tag_index[$tag . '_' . $level]++;
                }
                else
                { 
                    $current[$tag] = array (
                        $current[$tag],
                        $result
                    ); 
                    $repeated_tag_index[$tag . '_' . $level] = 2;
                    if (isset ($current[$tag . '_attr']))
                    {
                        $current[$tag]['0_attr'] = $current[$tag . '_attr'];
                        unset ($current[$tag . '_attr']);
                    }
                }
                $last_item_index = $repeated_tag_index[$tag . '_' . $level] - 1;
                $current = & $current[$tag][$last_item_index];
            }
        }
        elseif ($type == "complete")
        {
            if (!isset ($current[$tag]))
            {
                $current[$tag] = $result;
                $repeated_tag_index[$tag . '_' . $level] = 1;
                if ($priority == 'tag' and $attributes_data)
                    $current[$tag . '_attr'] = $attributes_data;
            }
            else
            {
                if (isset ($current[$tag][0]) and is_array($current[$tag]))
                {
                    $current[$tag][$repeated_tag_index[$tag . '_' . $level]] = $result;
                    if ($priority == 'tag' and $get_attributes and $attributes_data)
                    {
                        $current[$tag][$repeated_tag_index[$tag . '_' . $level] . '_attr'] = $attributes_data;
                    }
                    $repeated_tag_index[$tag . '_' . $level]++;
                }
                else
                {
                    $current[$tag] = array (
                        $current[$tag],
                        $result
                    ); 
                    $repeated_tag_index[$tag . '_' . $level] = 1;
                    if ($priority == 'tag' and $get_attributes)
                    {
                        if (isset ($current[$tag . '_attr']))
                        { 
                            $current[$tag]['0_attr'] = $current[$tag . '_attr'];
                            unset ($current[$tag . '_attr']);
                        }
                        if ($attributes_data)
                        {
                            $current[$tag][$repeated_tag_index[$tag . '_' . $level] . '_attr'] = $attributes_data;
                        }
                    }
                    $repeated_tag_index[$tag . '_' . $level]++; //0 and 1 index is already taken
                }
            }
        }
        elseif ($type == 'close')
        {
            $current = & $parent[$level -1];
        }
    }

    return ($xml_array);
}

?>

2

4 Answers 4

1

Just check your source array using empty: http://php.net/empty and return "" is empty() returned true. Add this at the begining of your function:

if( empty($myArray) ) {
   return '';
}
Sign up to request clarification or add additional context in comments.

Comments

0

The empty array you see is the default value you set:

$result = array ();

You have the following alternatives:

  1. Keep it as is - empty elements will have an empty array as value.
  2. Set to "" (empty string) - empty elements will have an empty string as value.
  3. Set to NULL - empty elements will be dropped if they have siblings with the same element name. Single empty elements will be preserved.

Depending on your need just take the default of your choice.

Comments

0

I first thought array_walk_recursive would be a great option, but it ignores empty arrays in the function call.

I would create a function, something like this. It goes through an array recursively and replaces array with string. (something like this)

function replaceArrayToString($arr = array()) {
    $newArr = array();
    foreach($arr as $key=>$value)
    {
        if (is_array($value))
        {
           unset($arr[$key]);

            //Is it an empty array, make it a string
            if (empty($value)) {
                $newArr[$key] = '';
            }
            else {
                $newArr[$key] = replaceArrayToString($value);
            }

        }
        else {
            $newArr[$key] = $value; 
        }

    }
    return $newArr;

}

and then call it from the end of your existing function xml2array() before returning the array.

    elseif ($type == 'close')
        {
        $current = & $parent[$level -1];
        }
    }

    $xml_array = replaceArrayToString($xml_array);
    return ($xml_array);
}

Comments

0

use empty function to check if array is empty or not

return empty($xml_array)?"":$xml_array;

<?php
function xml2array($contents, $get_attributes = 1, $priority = 'tag') {

$parser = xml_parser_create('');
xml_parser_set_option($parser, XML_OPTION_TARGET_ENCODING, "UTF-8");
xml_parser_set_option($parser, XML_OPTION_CASE_FOLDING, 0);
xml_parser_set_option($parser, XML_OPTION_SKIP_WHITE, 1);
xml_parse_into_struct($parser, trim($contents), $xml_values);
xml_parser_free($parser);
if (!$xml_values)
    return; //Hmm...
$xml_array = array ();
$parents = array ();
$opened_tags = array ();
$arr = array ();
$current = & $xml_array;
$repeated_tag_index = array (); 
foreach ($xml_values as $data)
{
    unset ($attributes, $value);
    extract($data);
    $result = array ();
    $attributes_data = array ();
    if (isset ($value))
    {
        if ($priority == 'tag')
            $result = $value;
        else
            $result['value'] = $value;
    }
    if (isset ($attributes) and $get_attributes)
    {
        foreach ($attributes as $attr => $val)
        {
            if($attr == 'xsi:type') continue;
            if($attr == 'xsi:nil') continue;

            if ($priority == 'tag')
                $attributes_data[$attr] = $val;
            else
                $result['attr'][$attr] = $val; //Set all the attributes in a array called 'attr'
        }
    }
    if ($type == "open")
    { 
        $parent[$level -1] = & $current;
        if (!is_array($current) or (!in_array($tag, array_keys($current))))
        {
            $current[$tag] = $result;
            if ($attributes_data)
                $current[$tag . '_attr'] = $attributes_data;
            $repeated_tag_index[$tag . '_' . $level] = 1;
            $current = & $current[$tag];
        }
        else
        {
            if (isset ($current[$tag][0]))
            {
                $current[$tag][$repeated_tag_index[$tag . '_' . $level]] = $result;
                $repeated_tag_index[$tag . '_' . $level]++;
            }
            else
            { 
                $current[$tag] = array (
                    $current[$tag],
                    $result
                ); 
                $repeated_tag_index[$tag . '_' . $level] = 2;
                if (isset ($current[$tag . '_attr']))
                {
                    $current[$tag]['0_attr'] = $current[$tag . '_attr'];
                    unset ($current[$tag . '_attr']);
                }
            }
            $last_item_index = $repeated_tag_index[$tag . '_' . $level] - 1;
            $current = & $current[$tag][$last_item_index];
        }
    }
    elseif ($type == "complete")
    {
        if (!isset ($current[$tag]))
        {
            $current[$tag] = $result;
            $repeated_tag_index[$tag . '_' . $level] = 1;
            if ($priority == 'tag' and $attributes_data)
                $current[$tag . '_attr'] = $attributes_data;
        }
        else
        {
            if (isset ($current[$tag][0]) and is_array($current[$tag]))
            {
                $current[$tag][$repeated_tag_index[$tag . '_' . $level]] = $result;
                if ($priority == 'tag' and $get_attributes and $attributes_data)
                {
                    $current[$tag][$repeated_tag_index[$tag . '_' . $level] . '_attr'] = $attributes_data;
                }
                $repeated_tag_index[$tag . '_' . $level]++;
            }
            else
            {
                $current[$tag] = array (
                    $current[$tag],
                    $result
                ); 
                $repeated_tag_index[$tag . '_' . $level] = 1;
                if ($priority == 'tag' and $get_attributes)
                {
                    if (isset ($current[$tag . '_attr']))
                    { 
                        $current[$tag]['0_attr'] = $current[$tag . '_attr'];
                        unset ($current[$tag . '_attr']);
                    }
                    if ($attributes_data)
                    {
                        $current[$tag][$repeated_tag_index[$tag . '_' . $level] . '_attr'] = $attributes_data;
                    }
                }
                $repeated_tag_index[$tag . '_' . $level]++; //0 and 1 index is already taken
            }
        }
    }
    elseif ($type == 'close')
    {
        $current = & $parent[$level -1];
    }
}

return ($xml_array);
} ?>

Comments

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.