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);
}

?>

share|improve this question
1  
1  
empty($value) ? '' : $value; does spring to mind, as does simpleXML, for that matter – Elias Van Ootegem Apr 5 at 7:07

4 Answers

use empty function to check if array is empty or not

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

$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);

} ?>

share|improve this answer

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 "";
}
share|improve this answer

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.

share|improve this answer

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);
}
share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.