Иметь все элементы покупки

0

У меня проблемы с SELECT. Я работаю в MySQL.

Я хочу получить электронное письмо "consumidor", которое купило продукты ("Produto"), которые включают в себя все "Элементо".

Я сделал это:

SELECT C.email
FROM Consumidor C, composto composto, compra compra
WHERE C.numero = compra.consumidor

HAVING COUNT(DISTINCT composto.elemento) = ( SELECT COUNT(*)
                                             FROM Elemento E)

Но это не сработало. У меня есть только один результат, и я знаю, что там больше. Я знаю, что между WHERE и HAVING отсутствует недостающий материал.

ТАБЛИЦЫ

Create table  Consumidor  (
    numero  int(9),
    email   varchar(30) not null,
    sexo    char(1) not null,
    nascimento  date    not null,
    constraint Consumidor_sexo_RI001     check (sexo in ('F','M')),
    constraint Consumidor_unique_RI002  unique(email),
    constraint pk_Consumidor     primary key (numero)
);
Create table  Elemento  (
    codigo  char(3),
    nome    varchar(25) not null,
    pegadaEcologica int(2) not null,
    saude   int(2) not null,
    constraint pk_Elemento   primary key (codigo)
);
Create table  Produto  (
    codigo  int(6),
    marca   int(7),
    nome    varchar(50) not null,
    tipo    char(10),
    comercioJusto   char(1),
    constraint Produto_tipo_RI004   check (tipo in ('alimentac','lar','jardim','automov','viagem','electrodom')),
    constraint Produto_comercioJusto_RI005   check (comercioJusto in ('A','B','C','D')),
    constraint fk_Produto_marca  foreign key (marca) references Marca(numero) on delete cascade,
    constraint pk_Produto    primary key (codigo,marca)
);
Create table  compra  (
    produto int(6),
    prodMarca   int(7),
    consumidor  int(9),
    quantidade  decimal(10,3)   not null,
    constraint compra_quantidade_RI006  check (quantidade>0),
    constraint fk_compra_produto     foreign key (produto,prodMarca) references Produto(codigo,marca) on delete cascade,
    constraint fk_compra_consumidor  foreign key (consumidor) references Consumidor(numero) on delete cascade,
    constraint pk_compra     primary key (produto,prodMarca,consumidor)
);
Create table  composto  (
    produto int(6),
    prodMarca   int(7),
    elemento    char(3),
    percentagem decimal(4,1)    not null,
    constraint composto_percentagem_RI007   check (percentagem>0 and percentagem<=100),
    constraint fk_composto_produto   foreign key (produto,prodMarca) references Produto(codigo,marca) on delete cascade,
    constraint fk_composto_elemento  foreign key (elemento) references Elemento(codigo) on delete cascade,
    constraint pk_composto   primary key (produto,prodMarca,elemento)
);
Теги:
select
having

2 ответа

1
Лучший ответ

имеющий

Неправильное использование функции HAVING. Что вы говорите, так как количество elemento (Product Details) должно совпадать с количеством вашей Composto (Products to Product Details).

Причина, по которой вы получаете только 1 строку, заключается в том, что вы присоединяетесь к Count или количеству строк из таблицы "Сведения о продукте" к количеству элементов, которые вы получили.

Попробуй это:

SELECT COUNT(*) FROM Elemento E

и вы увидите, что есть только одна единственная сумма, которая возвращается (количество фактической информации о товаре у вас есть).

Теперь попробуйте:

SELECT COUNT(DISTINCT composto.elemento) FROM composto

и вы увидите, что цифры совпадают.

Все, что вы делаете, это подсчет количества элементов. Это явно не то, что вы ищете, поскольку это не правильный способ улучшить ваши результаты.

Реляционные объединения

Кроме того, вы не правильно присоединяетесь к своим таблицам. MySQL - это " реляционная база данных ", что означает, что вам нужно конкретно определить "отношения" между вашими объектами (таблицами).

Для начала вам необходимо обновить свой запрос, чтобы исправить свои соединения:

 SELECT Customer.email, ProductDetails.nome
 FROM Consumidor Customer

    -- Joins the Consumidor (consumer) table to the Compra (sales) table
    INNER JOIN compra Sales
        ON Customer.numero = Sales.consumidor

    -- Joins the sales to the Produto (products) table
    INNER JOIN Producto Product
        ON Sales.produto = Product.codigo

    -- Joins the composto (Composite Key) table to the elemento (Product Details) table
    INNER JOIN composto
        ON composto.produto = Product.codigo

    -- Now get the Product details
    INNER JOIN elemento ProductDetails
        ON composto.elemento = ProductDetails.codigo

Теперь ваши соединения должны работать правильно, вы получите Person (Customer), продукты, которые они купили (compra), и информацию о продуктах.

Получите результаты

Я предполагаю, что вы хотите, это подмножество Produto (Products). Если это правильно, то вам нужно правильно определить ваши предикаты, используя предложение "WHERE":

SELECT Customer.email, ProductDetails.nome
FROM Consumidor Customer

    -- Joins the Consumidor (consumer) table to the Compra (sales) table
    INNER JOIN compra Sales
        ON Customer.numero = Sales.consumidor

    -- Joins the sales to the Produto (products) table
    INNER JOIN Producto Product
        ON Sales.produto = Product.codigo

    -- Joins the composto (Composite Key) table to the elemento (Product Details) table
    INNER JOIN composto
        ON composto.produto = Product.codigo

    -- Now get the Product details
    INNER JOIN elemento ProductDetails
        ON composto.elemento = ProductDetails.codigo
-- You can search for whatever matches your criteria here    
WHERE Customer.nome = 'Möoz' -- Finds all products that user 'Möoz' has bought

Вы также можете добавить или удалить предикаты в своем предложении WHERE, чтобы уточнить ваш поиск:

WHERE ProductDetails.pegadaEcologica = 'Low' --searches for a 'low ecological footprint' product only

или же

WHERE ProductDetails.nome = 'Black Show' -- Searches for black shoes in the name of the product

или же

WHERE ProductDetails.codigo = 35 -- Searches for the item with the ID of 35

....

  • 0
    Спасибо, это сработало, и теперь я понимаю это лучше. Спасибо ;)
0

Я не могу проверить это, поэтому вы можете получить некоторые синтаксические ошибки. Попробуйте и посмотрите, работает ли это:

-- Get e-mail of consumer who bought products which include all elements
SELECT cdr.email
FROM compra cmp -- Get all purchases
INNER JOIN consumidor cdr ON cmp.consumidor = cdr.numero -- Get consumer info
WHERE (cmp.produto, cmp.prodMarca) IN ( -- Only look at purchases which included products that included all elements
    SELECT pto.codigo, pto.marca
    FROM produto pto -- Get all products
    INNER JOIN composto cpt ON pto.codigo = cpt.produto AND cpt.prodMarca = pto.marca -- Get all elements defined for each product
    HAVING COUNT(*) = (SELECT COUNT(*) FROM elemento) -- Only return products that have all elements
    GROUP BY pto.codigo, pto.marca
);

Кроме того, вы можете захотеть сохранить одинаковые или похожие имена столбцов для ссылок на PK/FK. Это упрощает чтение и понимание вашей SQL/схемы. Дайте мне знать, если это сработает.

Ещё вопросы

Сообщество Overcoder
Наверх
Меню