0

Using the following Tables:

CREATE TABLE CUSTOMERS
(customerID     INT     PRIMARY KEY,
customerFullName        VARCHAR(20) NOT NULL,
customerStreet      VARCHAR(40) NOT NULL,
customerState       VARCHAR(15) NOT NULL,
customerCity        VARCHAR(20) NOT NULL,
customerZip     VARCHAR(15) NOT NULL);

CREATE TABLE VEHICLES
(vehicleVIN     VARCHAR(25) PRIMARY KEY,
vehicleType     VARCHAR(10) NOT NULL CHECK (lower(vehicleType) IN ('compact', 'midsize', 'fullsize', 'suv', 'truck')),
vehicleMake     VARCHAR(15) NOT NULL,
vehicleModel        VARCHAR(15) NOT NULL,
vehicleWhereFrom    VARCHAR(20) NOT NULL CHECK (lower(vehicleWhereFrom) IN ('maryland','virginia','washington, d.c.')),
vehicleWholesaleCost    DECIMAL(9,2)    NOT NULL,
vehicleTradeID      INT);

CREATE TABLE SALES
(saleID         INT     PRIMARY KEY,
grossSalePrice      DECIMAL(9,2),
vehicleStatus       VARCHAR(10) NOT NULL CHECK (lower(vehicleStatus) IN ('available', 'sold', 'pending')),
saleDate        DATE,
saleMileage     INT,
customerID      INT,
salespersonID       INT,
vehicleVIN      VARCHAR(25),
CONSTRAINT SALES_FK1 FOREIGN KEY (customerID) REFERENCES CUSTOMERS(customerID),
CONSTRAINT SALES_FK2 FOREIGN KEY (vehicleVIN) REFERENCES VEHICLES(vehicleVIN));

I have built the following query to display the vehicleMake that was involved in the most sales and the customerFullName of all who purchased a vehicle of that make:

SELECT VEHICLES.vehicleMake, CUSTOMERS.customerFullName
FROM SALES
JOIN CUSTOMERS on SALES.customerID = CUSTOMERS.customerID
    JOIN(
        SELECT SALES.vehicleVIN, VEHICLES.vehicleMake
        FROM SALES
          JOIN VEHICLES ON SALES.vehicleVIN = VEHICLES.vehicleVIN
          GROUP BY SALES.vehicleVIN, VEHICLES.vehicleMake
          HAVING COUNT(SALES.vehicleVIN) >= ALL
          (SELECT COUNT(SALES.vehicleVIN)
             FROM SALES
               INNER JOIN VEHICLES ON SALES.vehicleVIN=VEHICLES.vehicleVIN
               GROUP BY VEHICLES.vehicleMake))
      VEHICLES ON SALES.vehicleVIN = VEHICLES.vehicleVIN
      ORDER BY CUSTOMERS.customerFullName;

When I run this in my Oracle NOVA DB, I only get "no rows selected" as a result. I suspect this is because the following clause is counting the number of occurrences that a vehicleVIN is sold, instead of counting the number of occurrences that a vehicleMake is sold.

HAVING COUNT(SALES.vehicleVIN) >= ALL
          (SELECT COUNT(SALES.vehicleVIN)
             FROM SALES
               INNER JOIN VEHICLES ON SALES.vehicleVin=VEHICLES.vehicleVIN
               GROUP BY VEHICLES.vehicleMake))
      VEHICLES ON SALES.vehicleVIN = VEHICLES.vehicleVIN
      ORDER BY CUSTOMERS.customerFullName;

How would I change this SELECT Count subquery to count the number of vehicleMake occurences instead of the number of vehicleVIN occurrences? The output I'm looking for is:

vehicleMake     customerFullName
CAR2            Bob Jim
CAR2            Jim Bob
CAR2            Steve France
CAR2            Tom Williams
CAR2            John Johnson

It should only display the vehicleMake of the vehicleMake that was sold the most, and the customerFullName of those who purchased any vehicle of that make. Here is the link to SQL Fiddle if you want to see the Schema I've built: http://sqlfiddle.com/#!4/b0ac3a

StevenC
  • 109
  • 1
  • 20
  • 2
    Create a simplified example with dummy tables and dummy data. Work it down to the smallest possible proof that you're getting different behavior in each environment *(there by eliminating everything that's not relevant)*. Then post that example. *(My experience is that 9 times out of 10, so not always, the difference is the data not the environment. The first task should be to prove beyond doubt that it **is** the environment.)* – MatBailie Feb 01 '18 at 15:56
  • Do you have the same data in both places? I usually try to debug things like this by removing conditions and displaying more data. For example, remove the HAVING clause and display `count(sales.vehicleVIN)` and `(select count(...))` in your output. – kfinity Feb 01 '18 at 16:11
  • 1
    Eureka! Great advice. @MatBailie, your 9/10 experience just went up to 10/11. It turns out that it actually wasn't a DB error, it was how I was inputting data to the tables. Out of pure laziness, I was just re-using VIN's for the vehicleVIN input in SQL fiddler, whereas I had different VIN's for each vehicleVIN input on my main spool file. With that being said, my issue is actually based on the 'HAVING COUNT(SALES.vehicleVIN) >= ALL' subquery. I need to find a way to make this count the number of vehicleMake occurrences instead of the number of vehicleVIN occurrences. – StevenC Feb 01 '18 at 16:56
  • @StevenC That would be a new question, I'm traveling now, so not likely to answer from my phone, but I'm sure someone will :) *(In the new question provide a link to your example data in SQLFiddle.)* – MatBailie Feb 01 '18 at 17:37
  • @MatBailie Thanks! I went ahead and added the SQL Fiddle Link as well. – StevenC Feb 01 '18 at 18:33
  • Your expected results don't match your sample data. – MatBailie Feb 01 '18 at 19:59

1 Answers1

1

http://sqlfiddle.com/#!4/b0ac3a/67

WITH
  tallied_sales AS
(
  SELECT
    SALES.*,
    VEHICLES.vehicleMake,
    COUNT(*) OVER (PARTITION BY VEHICLES.vehicleMake)   AS vehicleMakeSales
  FROM
    SALES
  INNER JOIN
    VEHICLES
      ON VEHICLES.vehicleVIN  = SALES.vehicleVIN
),
  ranked_sales AS
(
  SELECT
    tallied_sales.*,
    RANK() OVER (ORDER BY vehicleMakeSales DESC)   AS vehicleMakeSalesRank
  FROM
    tallied_sales
)
SELECT
  *
FROM
  ranked_sales
INNER JOIN
  CUSTOMERS
    ON CUSTOMERS.customerID = ranked_sales.customerID
WHERE
  ranked_sales.vehicleMakeSalesRank = 1
;
MatBailie
  • 83,401
  • 18
  • 103
  • 137
  • Yes, the output data doesn't completely match. this as far as the names, makes. My apologies for that! This works! Only one question - How do I limit it to only show the customerFirName and vehicleMake? I don't need the VIN, customerID, customerMIName, customerLasName. the saleID is ok but not required. – StevenC Feb 01 '18 at 20:18
  • 1
    Ummmm, `SELECT CUSTOMERS.customerFirName, ranked_sales.vehicleMake` instead of `SELECT *`? – MatBailie Feb 01 '18 at 20:21
  • LMAO! Duh. I was forgetting the ranked_sales and was just writing vehicleMake. UGH! What a long day. Thank you so much again for the help. This has done the trick. – StevenC Feb 01 '18 at 20:24
  • feel free to upvote and accept, so I can get 200 for today ;) – MatBailie Feb 01 '18 at 20:25
  • Done. You earned it! – StevenC Feb 01 '18 at 20:26