PHP: Process all items within a multidimensional array

How can I get this:
$content = 'Spaß Vergnügen Fröhlichkeit!';
echo numerichtmlentities($content);

function numerichtmlentities($words) {
  mb_internal_encoding("UTF-8");
  $new_words = '';
  $words = html_entity_decode($words,ENT_COMPAT,'UTF-8');
  for($i=0; $i < mb_strlen($words); $i++) {
    $letter = mb_substr($words, $i, 1);
    if(!preg_match('/[-,.\(\)a-zA-Z0-9 ]/usm', $letter)) {
      $new_words .= '&#'.uniord($letter).';';
    }
    else {
      $new_words .= $letter;
    }
  }
  return $new_words;
}

Open in new window

to work with an array?  Could it be modified so that It processes any array I send to it?  
$content = array(
    array('es', array('div1' => "sólo", 'div2' => "diversión", 'div3' => 'desvío!')),
    array('de', array('div1' => "Spaß", 'div2' => "Vergnügen", 'div3' => 'Fröhlichkeit'))
);

echo json_encode(numerichtmlentities($content));

Open in new window


Thanks!
LVL 10
skijAsked:
Who is Participating?

[Product update] Infrastructure Analysis Tool is now available with Business Accounts.Learn More

x
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

Julian HansenCommented:
The function takes a string of space delimited words.

Arrays can be turned into strings using the implode function
http://php.net/manual/en/function.implode.php

In your example you could probably do something like this.
$content = array(
    array('es', array('div1' => "sólo", 'div2' => "diversión", 'div3' => 'desvío!')),
    array('de', array('div1' => "Spaß", 'div2' => "Vergnügen", 'div3' => 'Fröhlichkeit'))
);

$string = implode(' ', $content['de']);
echo numerichtmlentities($string);

Open in new window

Ray PaseurCommented:
I don't think you need all the moving parts in the functions here.  It seems not only correct, but also much simpler just to rely on the native behavior of JSON encoding.  You might also want to eliminate the top-level array, since it seems unnecessary (but I don't know for sure).  Maybe the language code could be an array key.

See: http://iconoun.com/demo/temp_skij.php
<?php // demo/temp_skij.php
/**
 * SEE: http://www.experts-exchange.com/questions/28689096/PHP-Process-all-items-within-a-multidimensional-array.html
 */
error_reporting(E_ALL);

// SET THE BROWSER CHARACTER SET
echo '<meta charset="utf-8" />';

// MAKE THE BROWSER OUTPUT EASY TO READ
echo '<pre>';

// TEST DATA FROM THE POST AT EE
$content = array(
    array('es', array('div1' => "sólo", 'div2' => "diversión", 'div3' => 'desvío!')),
    array('de', array('div1' => "Spaß", 'div2' => "Vergnügen", 'div3' => 'Fröhlichkeit'))
);

// ENCODE THE DATA AND DISPLAY IT
$jso = json_encode($content);
echo htmlentities($jso);
echo PHP_EOL;

// DECODE THE DATA AND DISPLAY IT
$obj = json_decode($jso);
var_dump($obj);
echo PHP_EOL;

Open in new window

Outputs:
[["es",{"div1":"s\u00f3lo","div2":"diversi\u00f3n","div3":"desv\u00edo!"}],["de",{"div1":"Spa\u00df","div2":"Vergn\u00fcgen","div3":"Fr\u00f6hlichkeit"}]]
array(2) {
  [0]=>
  array(2) {
    [0]=>
    string(2) "es"
    [1]=>
    object(stdClass)#1 (3) {
      ["div1"]=>
      string(5) "sólo"
      ["div2"]=>
      string(10) "diversión"
      ["div3"]=>
      string(8) "desvío!"
    }
  }
  [1]=>
  array(2) {
    [0]=>
    string(2) "de"
    [1]=>
    object(stdClass)#2 (3) {
      ["div1"]=>
      string(5) "Spaß"
      ["div2"]=>
      string(10) "Vergnügen"
      ["div3"]=>
      string(13) "Fröhlichkeit"
    }
  }
}

Open in new window

skijAuthor Commented:
Thank you both, but you are missing the point of my question.  I need to be able to process any array of any size with any number of dimensions / levels.  

How can I make a function walk through any array of any size with any number of dimensions?
Build an E-Commerce Site with Angular 5

Learn how to build an E-Commerce site with Angular 5, a JavaScript framework used by developers to build web, desktop, and mobile applications.

Terry WoodsIT GuruCommented:
Not sure this will work, but you could give it a try:

function numerichtmlentities(&$words) {
  if(is_array($words)) {
    array_walk_recursive($words, 'numerichtmlentities');
    return;
  }
  mb_internal_encoding("UTF-8");
  $new_words = '';
  $words = html_entity_decode($words,ENT_COMPAT,'UTF-8');
  for($i=0; $i < mb_strlen($words); $i++) {
    $letter = mb_substr($words, $i, 1);
    if(!preg_match('/[-,.\(\)a-zA-Z0-9 ]/usm', $letter)) {
      $new_words .= '&#'.uniord($letter).';';
    }
    else {
      $new_words .= $letter;
    }
  }
  $words = $new_words;
}

echo json_encode(numerichtmlentities($content));

Open in new window

NerdsOfTechTechnology ScientistCommented:
To somewhat answer your final question regarding the ability to process a variable multidimensional array, one method is using a recursive function.

Some programmers say use count() with recursion first to see how many elements exist.

In essence, the recursive function strategy would involve the initial foreach loop, a variable to keep track of  the "level", an if statement that determines if the current element is an array (recursive function called on element) or not (non-array item), and an optional counter to help determine the progress toward the maximum count of elements.
Ray PaseurCommented:
How can I make a function walk through any array of any size with any number of dimensions?
Sometimes examples make it hard to know what the "real" question is.

 JSON has native support for UTF-8, so the entire assembly of code in the original question appears to be unnecessary.  

PHP has native support for closures and callbacks, and has had the array_walk_recursive() function for several years.  Like all functions it's documented in the online man pages.  If you read that documentation and it's still not what you want, please post back and give us a different example, not the JSON thing - it appears to be confusing and maybe a red herring.
Terry WoodsIT GuruCommented:
That's the function I used in my code :-)
Ray PaseurCommented:
@Terry:

Ha!  I never read your code snippet.  :-)

It's the right function for recursion, of course, but there is no reason to do all the processing that the question assumes!

Anyway, I think we got this one covered.  All the best, ~Ray
skijAuthor Commented:
Thank you all for your comments and ideas.  Ray, I understand your point about this being somewhat redundant.

Terry, I tried your code and it returns a null result.  Below is an example.

What can be done to get a good result?
<?php

$content = array('z','x','!',
    array('es', array('div1' => "sólo", 'div2' => "diversión", 'div3' => 'desvío!')),
    array('de', array('div1' => "Spaß", 'div2' => "Vergnügen", 'div3' => 'Fröhlichkeit'))
);

echo json_encode(numerichtmlentities($content));

function numerichtmlentities(&$words) {
  if(is_array($words)) {
    array_walk_recursive($words, 'numerichtmlentities');
    return;
  }
  mb_internal_encoding("UTF-8");
  $new_words = '';
  $words = html_entity_decode($words,ENT_COMPAT,'UTF-8');
  for($i=0; $i < mb_strlen($words); $i++) {
    $letter = mb_substr($words, $i, 1);
    if(!preg_match('/[-,.\(\)a-zA-Z0-9 ]/usm', $letter)) {
      $new_words .= '&#'.uniord($letter).';';
    }
    else {
      $new_words .= $letter;
    }
  }
  $words = $new_words;
}

function uniord($u) {
    $k = mb_convert_encoding($u, 'UCS-2LE', 'UTF-8');
    $k1 = ord(substr($k, 0, 1));
    $k2 = ord(substr($k, 1, 1));
    return $k2 * 256 + $k1;
}

?>

Open in new window

Terry WoodsIT GuruCommented:
<?php

$content = array('z','x','!',
    array('es', array('div1' => "sólo", 'div2' => "diversión", 'div3' => 'desvío!')),
    array('de', array('div1' => "Spaß", 'div2' => "Vergnügen", 'div3' => 'Fröhlichkeit'))
);

echo json_encode(numerichtmlentities($content));

function numerichtmlentities(&$words) {
  if(is_array($words)) {
    array_walk_recursive($words, 'numerichtmlentities');
    return $words;
  }
  mb_internal_encoding("UTF-8");
  $new_words = '';
  $words = html_entity_decode($words,ENT_COMPAT,'UTF-8');
  for($i=0; $i < mb_strlen($words); $i++) {
    $letter = mb_substr($words, $i, 1);
    if(!preg_match('/[-,.\(\)a-zA-Z0-9 ]/usm', $letter)) {
      $new_words .= '&#'.uniord($letter).';';
    }
    else {
      $new_words .= $letter;
    }
  }
  $words = $new_words;
}

function uniord($u) {
    $k = mb_convert_encoding($u, 'UCS-2LE', 'UTF-8');
    $k1 = ord(substr($k, 0, 1));
    $k2 = ord(substr($k, 1, 1));
    return $k2 * 256 + $k1;
}

?>

                                          

Open in new window

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
PHP

From novice to tech pro — start learning today.