将停止词的中间部分改为星号PHP

I've two arrays, words and stop_words. I'd like to use stop_words to see matches in words and replace matches with a w**d.

So far:

$words_arr = explode(",",$result[0]->words);
$words_stop_arr = json_decode($settings['words_stop']);
print_r(str_ireplace($words_stop_arr, "****", $words_arr));

words_arr ->

Array ( [0] => sex [1] => drugs [2] => rock [3] => lamba [4] => runner [5] => rule [6] => going [7] => war [8] => work [9] => eat [10] => program [11] => photography [12] => cart [13] => wart [14] => jungle [15] => dick )

And stop words ->

Array ( [0] => dick [1] => orgy [2] => suck [3] => rape )

So dick should be changed into d**k. With my current implementation I just change everything with 4 asterisk... which is not desired...

Here's a function to censorize an array, based on what you're looking for :

function censorize(&$word, $k, $blacklist) {
    if(array_search($word, $blacklist) !== false) {
        $warr = str_split($word);
        $word = $warr[0]
                .implode('', array_fill(0, count($warr)-2, '*'))
                .end($warr);
    }
}

$words_arr      = array('allowed', 'censored', 'sex', 'drugs', 'rock', 'lamba', 'runner', 'rule', 'going', 'war', 'work', 'eat', 'program', 'photography', 'cart', 'wart', 'jungle', 'tick');
$words_stop_arr = array('censored', 'tick', 'orga', 'sack', 'rave');

array_walk($words_arr, 'censorize', $words_stop_arr);

echo '<pre>';
var_dump($words_arr);
echo '</pre>';

Check it on PHP Sandbox

A slightly different string-based approach, that doesn't modify the original array:

function censor_words( $words ){
  static $censored; if ( !$censored ) {
    $censored = array_flip(array(
      'crazy', 'daffodil', 'example', 'list'
    ));
  }
  foreach ( $words as $key => $word ) {
    if ( isset($censored[$word]) ) {
      $words[$key] = str_pad($word{0},strlen($word)-1,'*').substr($word, -1);
    }
  }
  return $words;
}

Usage:

$words_arr = array('hello', 'crazy', 'world', 'example', 'array');

print_r( censor_words($words_arr) );