MySQL - 尝试计算值出现的次数

时间:2016-01-30 15:49:48

标签: mysql

编辑#2 - 我想我弄清楚为什么只使用COUNT(*)给我一个不正确的值。我简化了这个数据库并且没有考虑每天“有多行”的因素...我已经填写了另一张表来更好地说明问题。

我是sql的新手并且查看了类似的帖子,并按照建议尝试了GROUP BY和COUNT但我没有做对。我试图获得特定日期的总次数,因此如果有销售,我可以获得平均每天的书籍数量。

Table - book                        Table - sale_day

+-------+---------------------+     +-------+----------+------------+
|   ID  |   Title             |     |   ID  |   Day    |  Date      |
+-------+---------------------+     +-------+----------+------------+
|     1 | Pride & Prejudice   |     |     1 | Monday   | 2016-01-02 |
|     2 | The Little Prince   |     |     2 | Tuesday  | 2016-01-03 |
|     3 | Harry Potter        |     |     3 | Monday   | 2016-01-09 |
+-------+---------------------+     +-------+----------+------------+

表 - book_sale

+------+---------+-----------+-------------+
|  ID  | Book_ID | Book_Sold | SaleDay_ID  | 
+------+---------+-----------+-------------+
|    1 |      1  |         6 | 1           |
|    2 |      2  |         3 | 1           |
|    3 |      3  |         1 | 1           |
|    4 |      1  |         2 | 1           |
|    5 |      3  |         8 | 2           |
|    6 |      1  |         3 | 3           |
|    7 |      2  |         3 | 3           |
|    8 |      1  |         6 | 1           |
|    9 |      1  |         7 | 3           |
+------+---------+-----------+-------------+

SQL:

$result = mysql_query("
          SELECT book_id, title, SUM(book_sold) AS book_sold, day,    
                 COUNT(book_sale.id) AS book_count
          FROM book_sale 
          LEFT JOIN book ON book_sale.book_id = book.id 
          LEFT JOIN sale_day ON book_sale.saleday_id = sale_day.id 
          GROUP BY title, day");

输出[我得到了前3列,我试图得到第4列的值]:

+--------------------+------------+-------------+-----------------------+
|  Book              | Total Sold |    Day      |    Count of # Days    |
+--------------------+------------+-------------+-----------------------+
|  Pride & Prejudice |      24    |   Monday    |         2             |
|  The Little Prince |      6     |   Monday    |         2             |
|  Harry Potter      |      1     |   Monday    |         1             |
|  Harry Potter      |      8     |   Tuesday   |         1             |
+--------------------+------------+-------------+-----------------------+

我想要每天存在的天数,这样我就可以获得每天的平均值,如果那天有销售的话。例如。骄傲&偏见= 11/3 = 3.66667 /星期一。

我已经尝试了COUNT(天),但是我得到了一个不正确的值 - 我认为这是在计算“星期一”出现的次数,但显示的值并不依赖于每本书。

提前致谢!

编辑#1 - 每个人都给出了相同的答案,但我仍然无法得到正确的值,所以这里是代码的其余部分,以防错误出现在这里:(

while ($book_sale = mysql_fetch_array($result)) {
    echo "<table><tr><td>" . $book_sale['title'] . "</td><td>" .                
          $book_sale['book_sold']  . "</td><td>" . 
          $book_sale['day']  . "</td><td>" . 
          $book_sale['book_count'] . "</td></tr></table>"; 
}

3 个答案:

答案 0 :(得分:0)

您只想计算每组中bool_sold行的数量。由于您已经说过要加入其他未显示的表格,为了防止它们被计算在内,您需要使用distinct关键字来计算行数来自book_sale表。所以使用count(distinct <primary-key-of-table>)。像这样:

SELECT book_id, title, SUM(book_sold) AS book_sold, day,
    count(distinct book_sale.ID) as `Count of # Days`
    FROM book, book_sale 
    WHERE book_id = book.id  
    GROUP BY title, day
    ORDER BY `Count of # Days` desc;

注意:在创建以下测试用例后,编辑了表,数据和预期结果。测试用例适用于之前编辑的问题。

测试用例:

create table book (
ID int unsigned primary key auto_increment,
Title varchar(255) not null
) engine=innodb;

create table book_sale (
ID int unsigned primary key auto_increment,
Book_ID int unsigned not null,
Book_Sold int unsigned not null,
Day varchar(255) not null,
foreign key book_sale_Book_ID_key(Book_ID) references book(ID)
) engine=innodb;

insert into book
(ID, Title)
values
(1, 'Pride & Prejudice'),
(2, 'The Little Prince'),
(3, 'Harry Potter');

insert into book_sale
(ID, Book_ID, Book_Sold, Day)
values
(1, 1, 6, 'Monday'),
(2, 2, 3, 'Monday'),
(3, 3, 1, 'Monday'),
(4, 1, 2, 'Monday'),
(5, 3, 8, 'Tuesday'),
(6, 1, 3, 'Monday'),
(7, 2, 3, 'Monday');

结果:

mysql> SELECT book_id, title, SUM(book_sold) AS book_sold, day,
    ->     count(distinct book_sale.ID) as `Count of # Days`
    ->     FROM book, book_sale 
    ->     WHERE book_id = book.id  
    ->     GROUP BY title, day
    ->     ORDER BY `Count of # Days` desc;
+---------+-------------------+-----------+---------+-----------------+
| book_id | title             | book_sold | day     | Count of # Days |
+---------+-------------------+-----------+---------+-----------------+
|       1 | Pride & Prejudice |        11 | Monday  |               3 |
|       2 | The Little Prince |         6 | Monday  |               2 |
|       3 | Harry Potter      |         1 | Monday  |               1 |
|       3 | Harry Potter      |         8 | Tuesday |               1 |
+---------+-------------------+-----------+---------+-----------------+
4 rows in set (0.00 sec)

答案 1 :(得分:0)

您需要加入这两个表。一种简单的方法是使用on子句:

SELECT b.book_id, b.title, SUM(bs.book_sold) AS book_sold,
       COUNT(*) as NumDifferentDays
FROM book b JOIN
     book_sale bs
     on b.id = bs.book_id
GROUP BY b.book_id, b.title;

您每天都有一条记录,因此您只需要COUNT(*)来查找天数。密钥不在day中包含GROUP BY。要获得平均值,只需使用AVG(bs.book_sold)

答案 2 :(得分:0)

这似乎是一个有效的查询:

SELECT
  title AS "Book",
  SUM(book_sold) AS "Total Sold",
  day AS "Day",
  COUNT(book_sale.id) AS "Count of # Days"
FROM
  book_sale LEFT JOIN book ON book_sale.book_id = book.id
GROUP BY
  book.id, book_sale.day

小提琴:http://sqlfiddle.com/#!9/bf5fa/3