Implode Problem

Hi

I have an issue with items listed on a page, the items have 3 values associated with them, on a few pages not all the items are listed and this where the problems arise, the values assocated with each item are no longer kept in order, for example this would be a listing with all items listed and all is good

Item1 Item2 Item3 Item4
£1.00 £4.00 £7.00 £3.00
£2.00 £5.00 £8.00 £6.00
£3.00 £6.00 £9.00 £8.00

This would be a listing with only three items listed, in this example we are only showing Item1, Item2 and Item4, now what happens is Items 1 and 2 display fine but Item4 does not show any values

Item1 Item2 Item4
£1.00 £4.00
£2.00 £5.00
£3.00 £6.00

The values for each Item are stored in a DB like this
item_values 1.00,2.00.3.00,4.00
item_values1 1.00,2.00.3.00,4.00
item_values2 1.00,2.00.3.00,4.00

The code to call is

foreach($arr_items as $key_item => $val_item) {
					$val_item_img = str_replace("'", '', $val_item);
					$val_item_img = str_replace(chr(146), '', $val_item_img);
					$image = strtolower(str_replace(' ', '_', $val_item_img)) . '.gif';
					if (!empty($item_values[$key_item])) $low = $item_values[$key_item];
					if (empty($low)) $low = '0.00';
					if (!empty($item_values1[$key_item])) $mid = $item_values1[$key_item];
					if (empty($mid)) $mid = '0.00';
					if (!empty($item_values2[$key_item])) $high = $item_values2[$key_item];
					if (empty($high)) $high = '0.00';
					if ($low > 0) $low_text = "Low: {$item_currencies[$key_item]}{$low}<br />";
					else $low_text = '';
					if ($mid > 0) $mid_text = "Mid: {$item_currencies[$key_item]}{$mid}<br />";
					else $mid_text = '';
					if ($high > 0) $high_text = "High: {$item_currencies[$key_item]}{$high}";
					else $high_text = '';
					$arr_items[$key_item] = "<div class='list_items_img'><img src='_layouts/images/items/{$image}' alt='$val_item' /><br />$val_item<br />{$low_text}{$mid_text}{$high_text}</div>";}
				$this->currentItem[$val] = implode('', $arr_items);
			}
		}

Thanks John

My guess is the problem isn’t in this code and the original $arr_items in the foreach doesn’t have the data you’re looking for.

return this result to us please:


var_dump($arr_items);

Implode is best for dealing with one dimensional arrays with relatively simple string or numerical values. For more complex array to string conversion it is strongly recommended that you use [fphp]serialize[/fphp] / [fphp]unserialize[/fphp] or [fphp]json_encode[/fphp] / [fphp]json_decode[/fphp].

He wants a comma separated list (I assume for output to a page).

Thanks for the replies guys

Could you please explain what you mean by this?

This is all new to me

He wants you to add that line to your code, and give us the output it generates. As we think the issue is with how $arr_items is generated and not the code you posted.

Hi again, putting var_dump($arr_items); into the code didnt display anything, guessing I am putting in the wrong place, anyway I include all the code with this post, hopefully this will point to the problem


$this->vars['title'] = $this->currentItem['name'];
		$item_values = explode(',', $this->currentItem['item_values']);
		foreach($item_values as $key => $val) {
			if (empty($val)) $item_values[$key] = 0;
			$item_values[$key] = number_format($val, 2);
		}
		$item_values1 = explode(',', $this->currentItem['item_values1']);
		foreach($item_values1 as $key => $val) {
			if (empty($val)) $item_values1[$key] = 0;
			$item_values1[$key] = number_format($val, 2);
		}
		$item_values2 = explode(',', $this->currentItem['item_values2']);
		foreach($item_values2 as $key => $val) {
			if (empty($val)) $item_values2[$key] = 0;
			$item_values2[$key] = number_format($val, 2);
		}
		$item_currencies = explode(',', $this->currentItem['item_currencies']);
		foreach($item_currencies as $key => $val) {
			if ($val == 1) $item_currencies[$key] = '&pound;';
			else $item_currencies[$key] = '&euro;';
		}

		// items lists
		$arr = array('item_types', 'facilities', 'nearby_facilities');
		foreach($arr as $key => $val) {
			$sql_items = $this->db->QFetchRowArray("SELECT * FROM {$this->tables['fields']} WHERE (field='{$val}') ORDER BY id ASC;");
			if ($val == 'nearby_facilities') $miles = explode(',', $this->currentItem['nearby_miles']);
			$arr_items = array();
			foreach(explode(',', $this->currentItem[$val]) as $key_item => $val_item) {
				if (!empty($val_item) && !empty($sql_items[$key_item]['value'])) {
					if ($val == 'nearby_facilities') if ($miles[$key_item] == 1) array_push($arr_items, $sql_items[$key_item]['value'] . ' - ' . $miles[$key_item] . ' Mile');
					else array_push($arr_items, $sql_items[$key_item]['value'] . ' - ' . $miles[$key_item] . ' Miles');
					else array_push($arr_items, $sql_items[$key_item]['value']);
				}


			}
			if ($val == 'nearby_facilities') $this->currentItem[$val] = implode('<br />', $arr_items);
			else if ($val == 'facilities') {
				sort($arr_items);
				foreach($arr_items as $key_item => $val_item) {
					$val_item_img = str_replace("'", '', $val_item);
					$val_item_img = str_replace(chr(146), '', $val_item_img);
					$image = strtolower(str_replace(' ', '_', $val_item_img)) . '.gif';
					$arr_items[$key_item] = "<div class='list_facilities_img'><img src='_layouts/images/facilities/{$image}' alt='$val_item' /> $val_item</div>";

	
				}
				$this->currentItem[$val] = implode('', $arr_items);
			} else {
				foreach($arr_items as $key_item => $val_item) {
					$val_item_img = str_replace("'", '', $val_item);
					$val_item_img = str_replace(chr(146), '', $val_item_img);
					$image = strtolower(str_replace(' ', '_', $val_item_img)) . '.gif';
					if (!empty($item_values[$key_item])) $low = $item_values[$key_item];
					if (empty($low)) $low = '0.00';
					if (!empty($item_values1[$key_item])) $mid = $item_values1[$key_item];
					if (empty($mid)) $mid = '0.00';
					if (!empty($item_values2[$key_item])) $high = $item_values2[$key_item];
					if (empty($high)) $high = '0.00';
					if ($low > 0) $low_text = "Low: {$item_currencies[$key_item]}{$low}<br />";
					else $low_text = '';
					if ($mid > 0) $mid_text = "Mid: {$item_currencies[$key_item]}{$mid}<br />";
					else $mid_text = '';
					if ($high > 0) $high_text = "High: {$item_currencies[$key_item]}{$high}";
					else $high_text = '';
					$arr_items[$key_item] = "<div class='list_items_img'><img src='_layouts/images/items/{$image}' alt='$val_item' /><br />$val_item<br />{$low_text}{$mid_text}{$high_text}</div>";}
				$this->currentItem[$val] = implode('', $arr_items);
			}
		}

Thanks John

Change this

            } else { 
                foreach($arr_items as $key_item => $val_item) { 
                    $val_item_img = str_replace("'", '', $val_item); 
                    $val_item_img = str_replace(chr(146), '', $val_item_img); 
                    $image = strtolower(str_replace(' ', '_', $val_item_img)) . '.gif'; 
                    if (!empty($item_values[$key_item])) $low = $item_values[$key_item]; 
                    if (empty($low)) $low = '0.00'; 
                    if (!empty($item_values1[$key_item])) $mid = $item_values1[$key_item]; 
                    if (empty($mid)) $mid = '0.00'; 
                    if (!empty($item_values2[$key_item])) $high = $item_values2[$key_item]; 
                    if (empty($high)) $high = '0.00'; 
                    if ($low > 0) $low_text = "Low: {$item_currencies[$key_item]}{$low}<br />"; 
                    else $low_text = ''; 
                    if ($mid > 0) $mid_text = "Mid: {$item_currencies[$key_item]}{$mid}<br />"; 
                    else $mid_text = ''; 
                    if ($high > 0) $high_text = "High: {$item_currencies[$key_item]}{$high}"; 
                    else $high_text = ''; 
                    $arr_items[$key_item] = "<div class='list_items_img'><img src='_layouts/images/items/{$image}' alt='$val_item' /><br />$val_item<br />{$low_text}{$mid_text}{$high_text}</div>";} 
                $this->currentItem[$val] = implode('', $arr_items); 
            } 

To

            } else { 
                var_dump($arr_items, $sql_items); // ADDED THIS LINE

                foreach($arr_items as $key_item => $val_item) { 
                    $val_item_img = str_replace("'", '', $val_item); 
                    $val_item_img = str_replace(chr(146), '', $val_item_img); 
                    $image = strtolower(str_replace(' ', '_', $val_item_img)) . '.gif'; 
                    if (!empty($item_values[$key_item])) $low = $item_values[$key_item]; 
                    if (empty($low)) $low = '0.00'; 
                    if (!empty($item_values1[$key_item])) $mid = $item_values1[$key_item]; 
                    if (empty($mid)) $mid = '0.00'; 
                    if (!empty($item_values2[$key_item])) $high = $item_values2[$key_item]; 
                    if (empty($high)) $high = '0.00'; 
                    if ($low > 0) $low_text = "Low: {$item_currencies[$key_item]}{$low}<br />"; 
                    else $low_text = ''; 
                    if ($mid > 0) $mid_text = "Mid: {$item_currencies[$key_item]}{$mid}<br />"; 
                    else $mid_text = ''; 
                    if ($high > 0) $high_text = "High: {$item_currencies[$key_item]}{$high}"; 
                    else $high_text = ''; 
                    $arr_items[$key_item] = "<div class='list_items_img'><img src='_layouts/images/items/{$image}' alt='$val_item' /><br />$val_item<br />{$low_text}{$mid_text}{$high_text}</div>";} 
                $this->currentItem[$val] = implode('', $arr_items); 
            } 

Then give us the output it generates.

Thanks for the reply

This is the output from a page that displays incorrectly

array(5) { 
  [0]=> string(5) "BandB" 
  [1]=> string(8) "1 Star Hotel" 
  [2]=> string(10) "2 Star Hotel" 
  [3]=> string(11) "3 Star Hotel" 
  [4]=> string(23) "Static 1 Star Hotel On Sale" 
} 
array(7) { 
  [0]=> array(3) { 
    ["field"]=> string(11) "item_types" 
    ["id"]=> string(1) "0" 
    ["value"]=> string(5) "BandB" 
  } 
  [1]=> array(3) { 
    ["field"]=> string(11) "item_types" 
    ["id"]=> string(1) "1" 
    ["value"]=> string(8) "1 Star Hotel" 
  } 
  [2]=> array(3) { 
    ["field"]=> string(11) "item_types" 
    ["id"]=> string(1) "2" 
    ["value"]=> string(10) "2 Star Hotel" 
  } 
  [3]=> array(3) { 
    ["field"]=> string(11) "item_types" 
    ["id"]=> string(1) "3" 
    ["value"]=> string(19) "4 Star Hotel" 
  } 
  [4]=> array(3) { 
    ["field"]=> string(11) "item_types" 
    ["id"]=> string(1) "4" 
    ["value"]=> string(11) "3 Star Hotel" 
  } 
  [5]=> array(3) { 
    ["field"]=> string(11) "item_types" 
    ["id"]=> string(1) "5" 
    ["value"]=> string(23) "Static 1 Star Hotel On Sale" 
  } 
  [6]=> array(3) { 
    ["field"]=> string(11) "item_types" 
    ["id"]=> string(1) "6" 
    ["value"]=> string(19) "Self Catering" 
  } 
}

We only have one price per item on this entry

The price entered for BandB, 1 Star Hotel and 2 Star Hotel are in the correct order, the price for 3 Star Hotel is being displayed under 5 Star Hotel for which no price has been entered

Can you change

var_dump($arr_items, $sql_items); // ADDED THIS LINE

To

var_dump($item_values, $item_values1, $item_values2); // ADDED THIS LINE

I missed those arrays and I’d like to see their values too.

On this page the prices for BandB, 1 Star Hotel and 2 Star Hotel are correct we have three prices for each of these items, the problem on this page is the prices for 3 Star Hotel for which we have two are listed under 4 Star Hotel for which we have no prices listed but we are showing as available.


array(5) {
[0]=> string(5) "BandB"
[1]=> string(8) "1 Star Hotel"
[2]=> string(10) "2 Star Hotel"
[3]=> string(11) "3 Star Hotel"
[4]=> string(23) "5 Star Hotel" }

array(7) {
[0]=> array(3) {
["field"]=> string(11) "item_types"
["id"]=> string(1) "0"
["value"]=> string(5) "BandB" }

[1]=> array(3) {
["field"]=> string(11) "item_types"
["id"]=> string(1) "1"
["value"]=> string(8) "1 Star Hotel" }

[2]=> array(3) {
["field"]=> string(11) "item_types"
["id"]=> string(1) "2"
["value"]=> string(10) "2 Star Hotel" }

[3]=> array(3) {
["field"]=> string(11) "item_types"
["id"]=> string(1) "3"
["value"]=> string(19) "4 Star Hotel" }

[4]=> array(3) {
["field"]=> string(11) "item_types"
["id"]=> string(1) "4"
["value"]=> string(11) "3 Star Hotel" }

[5]=> array(3) {
["field"]=> string(11) "item_types"
["id"]=> string(1) "5"
["value"]=> string(23) "5 Star Hotel" }

[6]=> array(3) {
["field"]=> string(11) "item_types"
["id"]=> string(1) "6"
["value"]=> string(19) "Self Catering" } }


array(7) {
[0]=> string(5) "11.00"
[1]=> string(5) "11.00"
[2]=> string(5) "11.00"
[3]=> string(4) "0.00"
[4]=> string(6) "290.00"
[5]=> string(4) "0.00"
[6]=> string(4) "0.00" }

array(7) {
[0]=> string(5) "11.00"
[1]=> string(5) "11.00"
[2]=> string(5) "11.00"
[3]=> string(4) "0.00"
[4]=> string(4) "0.00"
[5]=> string(4) "0.00"
[6]=> string(4) "0.00" }

array(7) {
[0]=> string(5) "18.00"
[1]=> string(5) "18.00"
[2]=> string(5) "18.00"
[3]=> string(4) "0.00"
[4]=> string(6) "450.00"
[5]=> string(4) "0.00"
[6]=> string(4) "0.00" }

Thanks for your time

John

Okay, this is going to take a bit to explain, but your issue is a mis-match between your index of one array, to the index of your other arrays.

In your code, you are looping through this array

array(5) {
[0]=> string(5) "BandB"
[1]=> string(8) "1 Star Hotel"
[2]=> string(10) "2 Star Hotel"
[3]=> string(11) "3 Star Hotel"
[4]=> string(23) "5 Star Hotel" } 

You are placing the index (0-4) into $key_item and the value into $val_item.

Then you are taking the $key_item and using it as the index to $item_values, $item_values2, and $item_values3 (shown below).

                    if (!empty($item_values[$key_item])) $low = $item_values[$key_item];  // HERE
                    if (empty($low)) $low = '0.00';
                    if (!empty($item_values1[$key_item])) $mid = $item_values1[$key_item];   // HERE
                    if (empty($mid)) $mid = '0.00';
                    if (!empty($item_values2[$key_item])) $high = $item_values2[$key_item];   // AND HERE
                    if (empty($high)) $high = '0.00'; 

So you are taking index 3, which is 3 Star Hotel and using index 3 of $item_values, $item_values2, and $item_values3 which is 0.00, 0.00, and 0.00 respectively.

There lies your problem. You can’t do that, because that isn’t the correct index for those arrays. To find the correct index, you need to match the $val_item to the value index in $sql_items

array(7) {
[0]=> array(3) {
["field"]=> string(11) "item_types"
["id"]=> string(1) "0"
["value"]=> string(5) "BandB" }

[1]=> array(3) {
["field"]=> string(11) "item_types"
["id"]=> string(1) "1"
["value"]=> string(8) "1 Star Hotel" }

[2]=> array(3) {
["field"]=> string(11) "item_types"
["id"]=> string(1) "2"
["value"]=> string(10) "2 Star Hotel" }

[3]=> array(3) {
["field"]=> string(11) "item_types"
["id"]=> string(1) "3"
["value"]=> string(19) "4 Star Hotel" }

[4]=> array(3) {
["field"]=> string(11) "item_types"
["id"]=> string(1) "4"
["value"]=> string(11) "3 Star Hotel" }

[5]=> array(3) {
["field"]=> string(11) "item_types"
["id"]=> string(1) "5"
["value"]=> string(23) "5 Star Hotel" }

[6]=> array(3) {
["field"]=> string(11) "item_types"
["id"]=> string(1) "6"
["value"]=> string(19) "Self Catering" } } 

As you can see the correct index for $item_values, $item_value2, and $item_values3 for 3 Star Hotel is 4. And if you look in those arrays, the value for index 4 is 290.00, 0.00, and 450.00 respectively.

So you need to look up the correct key.

$correctKey = findKey($val_item, $sql_items);

function findKey($value, $items)
{
  foreach ($items as $item)
  {
    if ($item['value'] == $value)
    {
       return $item['id'];
    }
  }

  return null;
}

There may be a better way to write that statement, but I’ll leave that for others to take as a challenge.

Now to implement that into your code:

function findKey($value, $items)
{
  foreach ($items as $item)
  {
    if ($item['value'] == $value)
    {
       return $item['id'];
    }
  }

  return null;
}

$this->vars['title'] = $this->currentItem['name'];
        $item_values = explode(',', $this->currentItem['item_values']);
        foreach($item_values as $key => $val) {
            if (empty($val)) $item_values[$key] = 0;
            $item_values[$key] = number_format($val, 2);
        }
        $item_values1 = explode(',', $this->currentItem['item_values1']);
        foreach($item_values1 as $key => $val) {
            if (empty($val)) $item_values1[$key] = 0;
            $item_values1[$key] = number_format($val, 2);
        }
        $item_values2 = explode(',', $this->currentItem['item_values2']);
        foreach($item_values2 as $key => $val) {
            if (empty($val)) $item_values2[$key] = 0;
            $item_values2[$key] = number_format($val, 2);
        }
        $item_currencies = explode(',', $this->currentItem['item_currencies']);
        foreach($item_currencies as $key => $val) {
            if ($val == 1) $item_currencies[$key] = '&pound;';
            else $item_currencies[$key] = '&euro;';
        }

        // items lists
        $arr = array('item_types', 'facilities', 'nearby_facilities');
        foreach($arr as $key => $val) {
            $sql_items = $this->db->QFetchRowArray("SELECT * FROM {$this->tables['fields']} WHERE (field='{$val}') ORDER BY id ASC;");
            if ($val == 'nearby_facilities') $miles = explode(',', $this->currentItem['nearby_miles']);
            $arr_items = array();
            foreach(explode(',', $this->currentItem[$val]) as $key_item => $val_item) {
                if (!empty($val_item) && !empty($sql_items[$key_item]['value'])) {
                    if ($val == 'nearby_facilities') if ($miles[$key_item] == 1) array_push($arr_items, $sql_items[$key_item]['value'] . ' - ' . $miles[$key_item] . ' Mile');
                    else array_push($arr_items, $sql_items[$key_item]['value'] . ' - ' . $miles[$key_item] . ' Miles');
                    else array_push($arr_items, $sql_items[$key_item]['value']);
                }


            }
            if ($val == 'nearby_facilities') $this->currentItem[$val] = implode('<br />', $arr_items);
            else if ($val == 'facilities') {
                sort($arr_items);
                foreach($arr_items as $key_item => $val_item) {
                    $val_item_img = str_replace("'", '', $val_item);
                    $val_item_img = str_replace(chr(146), '', $val_item_img);
                    $image = strtolower(str_replace(' ', '_', $val_item_img)) . '.gif';
                    $arr_items[$key_item] = "<div class='list_facilities_img'><img src='_layouts/images/facilities/{$image}' alt='$val_item' /> $val_item</div>";


                }
                $this->currentItem[$val] = implode('', $arr_items);
            } else {
                foreach($arr_items as $key_item => $val_item) {
                    $val_item_img = str_replace("'", '', $val_item);
                    $val_item_img = str_replace(chr(146), '', $val_item_img);
                    $image = strtolower(str_replace(' ', '_', $val_item_img)) . '.gif';
                    $correctKey = findKey($val_item, $sql_items);
                    if (!empty($item_values[$correctKey])) $low = $item_values[$correctKey];
                    if (empty($low)) $low = '0.00';
                    if (!empty($item_values1[$correctKey])) $mid = $item_values1[$correctKey];
                    if (empty($mid)) $mid = '0.00';
                    if (!empty($item_values2[$correctKey])) $high = $item_values2[$correctKey];
                    if (empty($high)) $high = '0.00';
                    if ($low > 0) $low_text = "Low: {$item_currencies[$key_item]}{$low}<br />";
                    else $low_text = '';
                    if ($mid > 0) $mid_text = "Mid: {$item_currencies[$key_item]}{$mid}<br />";
                    else $mid_text = '';
                    if ($high > 0) $high_text = "High: {$item_currencies[$key_item]}{$high}";
                    else $high_text = '';
                    $arr_items[$key_item] = "<div class='list_items_img'><img src='_layouts/images/items/{$image}' alt='$val_item' /><br />$val_item<br />{$low_text}{$mid_text}{$high_text}</div>";}
                $this->currentItem[$val] = implode('', $arr_items);
            }
        }  

You may need to make similar changes to $item_currencies so that it uses $correctKey instead of $key_item.

That worked :slight_smile: Thank you so much for all your time

Regards John