C# - Algoritm generare meniu


(Tudor) #1

Hei. Am de făcut un tagPage unde user-ul introduce un buget, iar eu trebuie să-i generez mai multe meniu formate din 3 feluri de mâncare care să fie până în bugetul alocat și să respect numărul de kcal zilnic recomandat.

Am încercat chestia asta:

            buget = Convert.ToInt32(textBox8.Text);

            OleDbConnection conn = new OleDbConnection(constr);

            conn.Open();

            OleDbCommand cmd = new OleDbCommand(@"SELECT * FROM Meniu WHERE felul = 1", conn);
            OleDbDataReader reader = cmd.ExecuteReader();

            while(reader.Read())
            {
                OleDbCommand cmd_2 = new OleDbCommand(@"SELECT * FROM Meniu WHERE felul = 2", conn);
                OleDbDataReader reader_2 = cmd_2.ExecuteReader();

                while (reader_2.Read())
                {
                    if (Convert.ToInt32(reader[3]) + Convert.ToInt32(reader_2[3]) < kcal && Convert.ToInt32(reader[4]) + Convert.ToInt32(reader_2[4]) < buget)
                    {
                        OleDbCommand cmd_3 = new OleDbCommand(@"SELECT * FROM Meniu WHERE felul = 3", conn);
                        OleDbDataReader reader_3 = cmd_3.ExecuteReader();

                        while (reader_2.Read())
                        {
                            if (Convert.ToInt32(reader[3]) + Convert.ToInt32(reader_2[3]) + Convert.ToInt32(reader_3[4]) <= kcal && Convert.ToInt32(reader[4]) + Convert.ToInt32(reader_2[4]) + Convert.ToInt32(reader_3[4]) <= buget)
                            {
                                OleDbCommand insert = new OleDbCommand(@"INSERT INTO Generate (felul1_id, felul2_id, felul3_id, kcal, pret) VALUES ('" + reader[1] + "','" + reader_2[1] + "','" + reader_3[1] + "'," + (Convert.ToInt32(reader[3]) + Convert.ToInt32(reader_2[3]) + Convert.ToInt32(reader_3[4])) + ", " + Convert.ToInt32(reader[4]) + Convert.ToInt32(reader_2[4]) + Convert.ToInt32(reader_3[4]) + ")", conn);
                                insert.ExecuteNonQuery();
                            }
                        }
                    }
                }
            }

Problema e că nu știu de ce, dar nu funcționează :frowning:


(cosmos) #2

Tu trebuie sa generezi tripletele care adunate dau 2500 (hai sa zicem ca acesta este nr recomandat de kcal)

Poti sa adaptezi la ce ai tu codul de mai jos

  public static void GenerateTriplets(int [] menu, int menuSize, int sum)
        {
            for (int i = 0; i < menuSize - 2; i++)
            {
                for (int j = i + 1; j < menuSize -1; j++)
                {
                    for (int k = j + 1; k < menuSize; k++)
                    {
                        if (menu[i] + menu[j] + menu[k] == sum)
                        {
                            Console.WriteLine("Felurile: {0}, {1}, {2}", menu[i], menu[j], menu[k]);
                        }
                    }
                }
            }
        }

unde:

  • menu[] este un array ce contine valorile nutritionale ale felurilor
  • menuSize reprezinta dimensiunea array-ului
  • sum reprezinta nr de kcal

int[] menu = new int []{ 1000, 1000, 500, 100, 1212, 2032, 100, 1000, 1400 }; GenerateTriplets(menu, menu.Length, 2500);

In link-ul de mai jos ai o varianta si cu sortarea array-ului. Vectorul il poti popula cu valori din baza de date

La fel poti proceda si pt buget.

Poti sa it simplifici din restrictiile problemei.


Codul l-am adaptat de aici

UPDATE

for (int i = 0; i < menuSize; i++)
{
        if ((menu[i] + menu[i + 1] + menu[i + 2]) == sum)
        {
             Console.WriteLine("Felurile: {0}, {1}, {2}", menu[i], menu[i + 1], menu[i + 2]);
        }
 }
Asta nu da rezultate duplicate

(Andrei) #3

Pe langa logica in sine, care trebuie sa-i dai de cap, am niste recomandari. Amesteci diverse layere in implementare:

  • UI (citesti textBox8.Text)
  • Storage (apelezi baza de date)
  • Business logic (generarea meniului cu felurile de mancare)

Ar trebui sa ai o separare, nu se le amesteci. Chiar daca le chemi din acelasi loc, implementarea lor efectiva e recomandat sa fie separata (din diverse motive, incluzand testabilitatea).

In plus, ai putea sa imbunatatesti si felul in care interoghezi baza de date pentru a fi mai optim. Logica din

Convert.ToInt32(reader[3]) + Convert.ToInt32(reader_2[3]) < kcal && Convert.ToInt32(reader[4]) + Convert.ToInt32(reader_2[4]) < buget

ar putea fi executata direct in baza de date, nu pe datele din memorie in client


(Tudor) #4

Solved. Extrageam coloanele gresite.