Wie ooo Wie kan mij helpen?


Waar ik naar opzoek ben is om de categorieën en de bijhorende producten uit de database te krijgen.

Onderstaand een voorbeeld van de database
Het betreft 3 tabellen category, products en relation

Categorieën (category)
[table]
[tr][td]id[/td][td]category[/td][/tr]
[tr][td]1[/td][td]Speelgoed[/td][/tr]
[tr][td]2[/td][td]Boeken[/td][/tr]
[tr][td]3[/td][td]Gereedschap[/td][/tr]
[tr][td]4[/td][td]Kantoorartikelen[/td][/tr]
[/table]

Producten (product)
[table]
[tr][td]id[/td][td]products[/td][/tr]
[tr][td]1[/td][td]Hamer[/td][/tr]
[tr][td]2[/td][td]Zaag[/td][/tr]
[tr][td]3[/td][td]Schroevendraaier[/td][/tr]
[tr][td]4[/td][td]Beitel[/td][/tr]
[tr][td]5[/td][td]Papier[/td][/tr]
[/table]

Koppeltabel (relation)
[table]
[tr][td]proid[/td][td]catid[/td][/tr]
[tr][td]3[/td][td]1[/td][/tr]
[tr][td]3[/td][td]2[/td][/tr]
[tr][td]3[/td][td]3[/td][/tr]
[tr][td]3[/td][td]4[/td][/tr]
[tr][td]4[/td][td]5[/td][/tr]
[/table]

Wat is nu een manier om dit eenvoudig te presenteren?

Gereedschap
- Hamer
- Zaag
- Schroevendraaien
- Beiten

Kantoorartikelen
- Papier
Ik denk dat het handiger is om zowel de categoriën als de producten in enkele tabel op te slaan, waarmee je een mooie 'tree' kan opbouwen. Pas geleden heb ik iemand nog een mooi advies gegeven over hoe je dit met een enkele query op kan lossen:

https://www.phphulp.nl/php/forum/topic/geen-submenu/103298/#747249

In dat topic kan je vast wat verder inlezen over deze manier van recursief uitlezen.
De oplossing is dus om in de productentabel een categorie-attribuut op te nemen. De koppeltabel kan dan geheel vervallen. Een koppeltabel is pas gewenst wanneer een product in meerdere categorieen gaat vallen.
Aad B op 15/02/2020 20:21:27

Een koppeltabel is pas gewenst wanneer een product in meerdere categorieen gaat vallen.

Maar als je het dan pas in moet bouwen is het wel een klere-klus. Als je dus nu al een beetje kunt verzinnen dat een artikel in meerdere categorieën zou kunnen gaan vallen (is een nietmachine een gereedschap of een kantoorartikel? plaats ze in beiden, dan vindt iedereen waar ie zoekt!), dan zou ik je toch aanbevelen om nu al met een koppeltabel te gaan werken. Voor de oplossing van Ariën hoef je dan alleen maar een extra join te maken.

select c.category,p.products
from category c
  join relation r on r.catid = c.id
  join product p on p.id = r.proid

Ook uit oogpunt van "producten" enerzijds en wat voor structuur dan ook anderzijd (categorieën, of tags, of wat dan ook) valt er misschien iets voor te zeggen om deze helemaal van elkaar gescheiden te houden. De producten staan in principe helemaal "los" van wat voor indelingslaag (of -lagen) die je hier bovenop bouwt, en inderdaad, mocht je je ooit nog eens bedenken hoe je deze indeelt, dan hoef je in ieder geval niets te slopen in de "stand alone" producten tabel.

@Stefan, kun je wat meer vertellen over waar de presentatie voor dient? Is dit een webshop? Of een soort van inventarislijst?
Het is moet een catalogus worden. Het is een soort webshop alleen dan zonder te kunnen bestellen.
Je hebt aan de ene kant een admin kant waarin je categorieën en producten kunt aanmaken.
Dit gebeurt los van elkaar, je moet dus eerst een categorie aanmaken om vervolgens deze te kunnen aanklikken bij het product die je op een andere pagina aanmaakt.

Omdat de administratiekant klaar is wil ik nu met een simple query en loop de categorieën een voor een laden en de daarbij horende producten aan de frontend


[size=xsmall]Toevoeging op 17/02/2020 11:18:02:[/size]

categories
[table]
[tr][td]id[/td][td]category[/td][/tr]
[tr][td]1[/td][td]Speelgoed[/td][/tr]
[tr][td]2[/td][td]Boeken[/td][/tr]
[tr][td]3[/td][td]Gereedschap[/td][/tr]
[tr][td]4[/td][td]Kantoorartikelen[/td][/tr]
[/table]

products
[table]
[tr][td]id[/td][td]product[/td][/tr]
[tr][td]1[/td][td]Hamer[/td][/tr]
[tr][td]2[/td][td]Zaag[/td][/tr]
[tr][td]3[/td][td]Schroevendraaier[/td][/tr]
[tr][td]4[/td][td]Beitel[/td][/tr]
[tr][td]5[/td][td]Papier[/td][/tr]
[/table]

relation
[table]
[tr][td]proid[/td][td]catid[/td][/tr]
[tr][td]1[/td][td]3[/td][/tr]
[tr][td]2[/td][td]3[/td][/tr]
[tr][td]3[/td][td]3[/td][/tr]
[tr][td]4[/td][td]3[/td][/tr]
[tr][td]5[/td][td]4[/td][/tr]
[/table]


<?php			
$sql	= " SELECT relation.catid, products.product, categories.category
			FROM relation 
			JOIN categories ON relation.catid = categories.id
			JOIN products ON relation.proid = products.id";
			
$result			= mysqli_query($connection, $sql); 			
while($row = mysqli_fetch_assoc($result)){	
?>
<h1><?php echo $row['category']; ?></h1>
<span><?php echo $row['product']; ?></span>
<?php
}
?>


Nu krijg ik als resultaat


<h1>Gereedschap</h1>
</span>Hamer</span>
<h1>Gereedschap</h1>
</span>Zaag</span>
<h1>Gereedschap</h1>
</span>Schroevendraaier</span>
<h1>Gereedschap</h1>
</span>Beitel</span>
<h1>Kantoorartikelen</h1>
</span>Papier</span>


De categorie naam word ook steeds meegepakt in het verhaal.
Hoe kan ik dit nu het beste aanpakken dat er een lijst ontstaat met de categorienaam de producten en dan pas de volgende categorienaam?

Doe ik dit met een query of maak ik arrays en los ik dit met php op, wat zouden jullie mij voor een suggesties geven?

[size=xsmall]Toevoeging op 17/02/2020 11:19:23:[/size]

ik had in mijn eerste voorbeeld de rijen verwisseld bij de relation tabel, deze heb ik aangepast.
Dit geeft het gewenste resultaat.
Categorie in het h1 element en de producten in deze categorie in het span element.
Nu een beetje stylen en je hebt een mooie catalogus.
<?php
$sql = "SELECT relation.catid, products.product, categories.category
FROM relation
JOIN categories ON relation.catid = categories.id
JOIN products ON relation.proid = products.id";

$output = [];
$result = mysqli_query($connection, $sql);
while ($row = mysqli_fetch_assoc($result)) {
$output[$row['category']][] = $row['product'];
}

foreach ($output as $category => $products) {
echo "<h1>$category</h1>";
foreach ($products as $product) {
echo "<span>$product</span>";
}
}
?>
Bedankt voor het antwoord :-)

Maar ik ben iets vergeten en dat is het volgende
In de categorie tabel heb ik een kolom met omschrijving en op de product pagina een kolom met de prijs.

De array die gecreeerd word met

<?php $output[$row['category']][] = $row['product'];?>


Bevat alleen de categorie en de naam van het product.
Kan ik met een multidimensional meerdere keys toevoegen? en die met een foreach uitlezen?

Dat je de categorienaam krijgt met de omschrijving met de daaraan gekoppelde producten met de prijs?


<?php
$sql = "SELECT relation.catid, products.product,  products.price, categories.category
        FROM relation
        JOIN categories ON relation.catid = categories.id
        JOIN products ON relation.proid = products.id";

$output = [];
$amounts[];
$result = mysqli_query($connection, $sql);
while ($row = mysqli_fetch_assoc($result)) {
    $output[$row['category']][] = $row['product'];
    $amounts[$row['product']][] = $row['price'];
}

foreach ($output as $category => $products) {
    echo "<h1>$category</h1>";
    //hier de omschrijving
    foreach ($products as $product) {
        echo "<span>$product</span>";
       //zelf heb ik dit geprobeerd.
        foreach($amounts as $amount => $price){
            echo $price;
        }
    }
}
?>
Kan ik met een multidimensional meerdere keys toevoegen? en die met een foreach uitlezen?
Dat je de categorienaam krijgt met de omschrijving met de daaraan gekoppelde producten met de prijs?


Ja waarom niet?

Zorg dat je voor alles keys aanmaakt, zodat je hier op een intuitieve manier aan kunt refereren.

Bouw bijvoorbeeld het array als volgt:
<?php
$categories = array(
    1 => array(
        'name' => 'category name',
        'description' => 'category description',
        // etc
        'products' => array(
            1 => array(
                'name' => 'product name',
                'price' => 'product price',
                // etc
            ),
        ),
    ),
);
?>

En hier kun je dan met een dubbele for(each) loop doorheen.
Hallo Thomas,


Ik heb zo een array gebouwd en een foreach gebruikt maar krijg alleen het laatste resultaat terug van de array

<?php
$output = array(
	1 => array(
		'name' => 'Speelgoed',
		'description' => 'In deze category zie je allemaal speelgoed',
		'products' => array(
			1 => array(
            	'productname' => 'Lego',
               	'price' => '12,95',
			),
		),	
		'products' => array(
			2 => array(
            	'productname' => 'Puzzel 1000 stukjes',
               	'price' => '19,95',
			),
		),	
	),
);
	
foreach($output as $category => $names){
	echo '<h1>'.$names['name'].'</h1>';
	echo '<div>'.$names['description'].'</div></br>';
	foreach($names['products'] as $products){
		echo '<div>'.$products['productname'].'</div></br>';
		echo '<div>'.$products['price'].'</div></br>';
	}
}
?>
De structuur is ook verkeerd? De tweede "products" key overschrijft de eerste? Je mist een subarray voor de tweede categorie, als product 2 daar onderdeel van uitmaakt. Voor elke categorie dien je een subarray aan te maken met bovenstaande structuur. Anders doet de buitenste foreach ook niet zoveel :p. Ik zou ook wat namen kiezen die eea wat beter omschrijven, bijvoorbeeld:
<?php
foreach ($output as $categoryId => $category) {
    // doe iets met $category hier
    foreach ($category['products'] as $productId => $product) {
        // doe iets met $product hier
    }
}
?>

Reageren