Simpelere increasement van een value binnen multi-array

Overzicht Reageren

Sponsored by: Vacatures door Monsterboard

Johan M

Johan M

05/04/2016 22:21:38
Quote Anchor link
Goedenavond,

Zie graag onderstaand voorbeeld, is er een manier om dit korter schrijven dan met 3 keer "$aArray['test'][$vValue]"?
Om redenen die niet zijn opgenomen in dit voorbeeld is hier een multidimensionale-array nodig, vandaar nu de 'test'-key.
N.b.: Ik ben me bewust van simpele functies als bijvoorbeeld count() en het gaat vanzelfsprekend niet om het opzoeken van het aantal keer dat 'a' voorkomt in $aVoorbeeld, dat zou een andere vraag zijn, het gaat mij om het korter schrijven van de regel waarop de key's worden aangemaakt zonder een Notice te krijgen dat de key niet bestaat (wanneer je bijvoorbeeld "$aArray['test'][$vValue]++;" of "$aArray['test'][$vValue] += 1;" zou doen:

Code (php)
PHP script in nieuw venster Selecteer het PHP script
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
<?php

$aVoorbeeld
= array('a', 'b', 'c', 'a', 'a', 'c', 'd');

$aArray = array();
foreach($aVoorbeeld AS $vValue)
{

        $aArray['test'][$vValue] = isset($aArray['test'][$vValue]) ? $aArray['test'][$vValue] + 1 : 1;
}


print_r($aArray);

/*
Gewenste output:

Array
(
    [test] => Array
        (
            [a] => 3
            [b] => 1
            [c] => 2
            [d] => 1
        )

)

*/

?>


Ik hoor het graag!
 
PHP hulp

PHP hulp

05/08/2020 01:34:11
 
Thomas van den Heuvel

Thomas van den Heuvel

06/04/2016 02:01:44
 
Johan M

Johan M

06/04/2016 07:24:08
Quote Anchor link
Dat begrijp ik, maar zoals ik probeerde te schrijven ben ik op zoek naar een nette, kortere manier om de array aan te maken. Iemand een idee?
 
Ozzie PHP

Ozzie PHP

06/04/2016 13:11:34
Quote Anchor link
>> Dat begrijp ik ...

Blijkbaar niet ;-)

Je had ook even moeite kunnen doen om de link te bekijken die Thomas hierboven aandraagt, want daar staat het antwoord gewoon in.

Code (php)
PHP script in nieuw venster Selecteer het PHP script
1
2
3
4
5
6
7
8
<?php

$aVoorbeeld
     = array('a', 'b', 'c', 'a', 'a', 'c', 'd');
$aArray['test'] = array_count_values($aVoorbeeld);

print_r($aArray);

?>
 
Johan M

Johan M

06/04/2016 13:35:41
Quote Anchor link
Bedankt voor je reactie Ozzie, uiteraard had ik het op php.net wel bekeken wat overigens overbodig was omdat ik hiermee al bekend was, dit beantwoord echter niet mijn vraag omdat het niet altijd $aArray['test'] betreft.

De array $aVoorbeeld bestaat uit meer regels dan alleen bovengenoemd (input waarop ik geen invloed heb) welke bestaan uit 2 type strings als waarde. Afhankelijk van het type wordt de eerste key van de array bepaald, waarna de volgende waarden uit de oorspronkelijke input-array hiervan het child worden, totdat er een nieuwe 1e-key-waarde langskomt.

De vraag blijft dus opnieuw onveranderd, vandaar dat ik in mijn beginpost al schreef dat het hier om een voorbeeld ging.

Om verdere verwarring te voorkomen en de reden waarom ik het hier vraag duidelijker te maken hierbij een duidelijkere voorbeeld-array:
Code (php)
PHP script in nieuw venster Selecteer het PHP script
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
<?php
$aVoorbeeld
= array('key_1', 'a', 'b', 'b', 'c', 'key_2', 'a', 'a', 'c', 'd', 'd');

/*
Gewenste output:

Array
(
    [key_1] => Array
        (
            [a] => 1
            [b] => 2
            [c] => 1
        )
    [key_2] => Array
        (
            [a] => 2
            [c] => 1
            [d] => 2
        )
)

*/

?>

Op deze input heb ik dus geen invloed anders had ik dit vanzelfsprekend anders aangepakt!

Ik ben niet iemand die voor het eerst met PHP bezig is of iemand die voor school een blog op moet zetten en te lui is om zelf iets te maken, ik probeer een serieuze vraag te stellen. Ik heb een werkend script welke ik hierboven voor de duidelijkheid (hoopte ik) ingekort had, jullie geven nuttige antwoorden, echter niet op de vraag zoals ik deze bedoelde te stellen.

Ik kan me vooral niet voorstellen dat er voor bovengenoemde oplossing op regel 8 van mijn eerste post geen simpelere manier is?
Gewijzigd op 06/04/2016 13:43:08 door Johan M
 
Jan de Laet

Jan de Laet

06/04/2016 13:45:17
Quote Anchor link
@Johan M, Hoe weet je uit jouw voorbeeld dat key_1 en key_2 "keys" zijn en a, b, c, d "values"?
 
Ozzie PHP

Ozzie PHP

06/04/2016 13:48:35
Quote Anchor link
Dan had je het beter de 1e keer even op de juiste manier uitgelegd, want nu schotel je een andere situatie voor dan je in eerste instantie deed.

Anyhow, die $aVoorbeeld is in werkelijkheid op dezelfde manier opgebouwd? Hoe weet je dan wat een key is en wat de childs zijn? Het zijn nu namelijk gewoon allemaal values.
 
Johan M

Johan M

06/04/2016 13:55:18
Quote Anchor link
Jan de Laet op 06/04/2016 13:45:17:
@Johan M, Hoe weet je uit jouw voorbeeld dat key_1 en key_2 "keys" zijn en a, b, c, d "values"?


Dit gebeurt d.m.v. een simpele vergelijking op het eerste gedeelte van elke string met substr(), de input betreft diverse gescande barcodes waarbij de werkordernummers gescande Code39 barcodes zijn en de artikelnummers gescande Code/EAN128-codes zijn. De scanners geven hierbij "BW-" terug bij Code39 en "KP-" terug aan het begin van de string bij Code128. Zoals gezegd heb ik dit niet verzonnen en heb ik hier verder geen invloed op helaas.


Ozzie PHP op 06/04/2016 13:48:35:
Dan had je het beter de 1e keer even op de juiste manier uitgelegd, want nu schotel je een andere situatie voor dan je in eerste instantie deed.

Anyhow, die $aVoorbeeld is in werkelijkheid op dezelfde manier opgebouwd? Hoe weet je dan wat een key is en wat de childs zijn? Het zijn nu namelijk gewoon allemaal values.


Ik hoopte het duidelijk uitgelegd te hebben door het voorbeeld simpel te houden, excuses als dit voor verwarring heeft gezorgd. Ik had er duidelijk bijstaan dat het een voorbeeld betrof en hoop dat er een nettere oplossing is voor regel 8.
Je vraag heb ik hierboven beantwoord!
 
Thomas van den Heuvel

Thomas van den Heuvel

06/04/2016 14:06:02
Quote Anchor link
Kun je dat array niet meteen fatsoenlijk opbouwen, of een fatsoeneringsstap tussenvoegen, dan kun je namelijk wederom van array_count_values() gebruik maken per subarray. Het probleem is ook niet zozeer het tellen an sich, maar het ontstaat meer door een gebrek aan structuur in je dataset...
 
Johan M

Johan M

06/04/2016 14:13:05
Quote Anchor link
Dat zou mooi zijn Thomas, maar hoe zou je dat doen in dit geval?

$aVoorbeeld = array('key_1', 'a', 'b', 'b', 'c', 'key_2', 'a', 'a', 'c', 'd', 'd');


Zoals gezegd heb ik geen invloed op deze input, dit is nou eenmaal hoe de scanners dit teruggeven.
 
Thomas van den Heuvel

Thomas van den Heuvel

06/04/2016 14:28:28
Quote Anchor link
Euh, een fatsoeneringsstap tussenvoegen?
Code (php)
PHP script in nieuw venster Selecteer het PHP script
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
<?php
// hierbij gaan we ervan uit dat je invoer klopt, en dus altijd begint met een key
function sortShizzleByKey($in) {
    $out = array();
    $currentKey = false;
    foreach ($in as $value) {
        // voer hier een controle uit om te zien of het een "key" betreft
        if (substr($value, 0, 4) === 'key_') {
            $currentKey = $value;
            $out[$currentKey] = array();
        }
else {
            $out[$currentKey][] = $value;
        }
    }

    return $out;
}


$test = array('key_1', 'a', 'b', 'b', 'c', 'key_2', 'a', 'a', 'c', 'd', 'd');

echo '<pre>'.print_r(sortShizzleByKey($test), true).'</pre>';
?>

And Bob's your uncle.
 
Johan M

Johan M

06/04/2016 14:44:35
Quote Anchor link
Bedankt Thomas,

Dit had ik zelf ook voor elkaar op deze manier:

Code (php)
PHP script in nieuw venster Selecteer het PHP script
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
<?php

$test
= array('key_1', 'a', 'b', 'b', 'c', 'key_2', 'a', 'a', 'c', 'd', 'd');

$currentKey = '';
foreach($test AS $vValue)
{

    if(substr($vValue, 0, 4) === 'key_')
    {

        $currentKey = $vValue;
    }

     else
    {
        $out[$currentKey][] = $vValue;
    }
}


echo '<pre>' . print_r($out, true) . '</pre>';

?>
Gewijzigd op 06/04/2016 14:46:19 door Johan M
 
Thomas van den Heuvel

Thomas van den Heuvel

06/04/2016 14:49:03
Quote Anchor link
Ja ok, maar dan ben je er toch al? Voer array_count_values() uit op elk van de subarrays en klaar?
Gewijzigd op 06/04/2016 14:50:22 door Thomas van den Heuvel
 
Johan M

Johan M

06/04/2016 16:42:41
Quote Anchor link
Dat klopt inderdaad Thomas, maar waarom zou dat je voorkeur hebben boven de oplossing uit mijn eerste post?


En om dan nog een beetje flauw te doen, is er echt geen oplossing om dit korter en netter te doen i.p.v. met 3 keer hetzelfde:

$aArray['test'][$vValue] = isset($aArray['test'][$vValue]) ? $aArray['test'][$vValue] + 1 : 1;
 
Thomas van den Heuvel

Thomas van den Heuvel

06/04/2016 16:52:01
Quote Anchor link
Blijkbaar is het op een bepaalde manier relevant dat je alles groepeert op key, zodat je daarna makkelijk(er) kunt gaan tellen. Waarom zou je datastructuur dit dan niet reflecteren?

Daarnaast zoek je enkel naar een "kortste oplossing" voor dit specifieke probleem, maar hoe gebruik je deze data verder? Dit zou moeten bepalen hoe je datastructuur er uit ziet, zodat je hier -in het algemeen- makkelijk mee kunt werken.

Wat is er op tegen om een probleem op te splitsen in deelproblemen, die mogelijk ook andere zaken gelijk tacklen (zoals het opzetten van een datastructuur die makkelijker is in het gebruik), in plaats van enkel een ad hoc oplossing te schrijven die enkel geschikt is voor een direct probleem?
 
Johan M

Johan M

06/04/2016 16:56:55
Quote Anchor link
Duidelijk verhaal Thomas, hartelijk dank voor het meedenken!
 
Pipo Clown

Pipo Clown

06/04/2016 17:57:27
Quote Anchor link
Code (php)
PHP script in nieuw venster Selecteer het PHP script
1
$aArray['test'][$vValue] = isset($aArray['test'][$vValue]) ? $aArray['test'][$vValue] + 1 : 1;


Dit is al een verkort geschreven stukje code voor een IF-THEN-ELSE

Wil je het duidelijker dan kan je het als volgt doen :

Code (php)
PHP script in nieuw venster Selecteer het PHP script
1
2
3
     if (isset($aArray['test'][$vValue]))
        $aArray['test'][$vValue] = $aArray['test'][$vValue] + 1;
     else $aArray['test'][$vValue] = 1;



De coderegel na het if-statement kan eventueel alsvolgt geschreven worden :

Code (php)
PHP script in nieuw venster Selecteer het PHP script
1
     $aArray['test'][$vValue]++;


Dat is wel iets korter.
 
- SanThe -

- SanThe -

06/04/2016 21:04:09
Quote Anchor link
Code (php)
PHP script in nieuw venster Selecteer het PHP script
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
<?php
$aVoorbeeld
= array('key_1', 'a', 'b', 'b', 'c', 'key_2', 'a', 'a', 'c', 'd', 'd');
$aArray = array();

$key = '';
while($shift = array_shift($aVoorbeeld))
{

    if(substr($shift, 0, 3) == 'key')
    {

        $key = $shift;
        $aArray[$key] = array();
    }

    else
    {
        $aArray[$key][$shift] = isset($aArray[$key][$shift]) ? $aArray[$key][$shift]+1 : 1;
    }
}


print_r($aArray);
?>
Gewijzigd op 06/04/2016 21:56:35 door - SanThe -
 



Overzicht Reageren

 
 

Om de gebruiksvriendelijkheid van onze website en diensten te optimaliseren maken wij gebruik van cookies. Deze cookies gebruiken wij voor functionaliteiten, analytische gegevens en marketing doeleinden. U vindt meer informatie in onze privacy statement.