开发者

Count the number of fields that are not empty in MySQL

开发者 https://www.devze.com 2022-12-24 11:32 出处:网络
I have a database of users where they can send messages to other users (up to four) and the ID of the message they sent is in their user row.

I have a database of users where they can send messages to other users (up to four) and the ID of the message they sent is in their user row.

Name    | Email       | Msg1 | Msg2 | Msg3 | Msg4
--------+-------------+------+------+------+-----
Pez     | me@me.com   |  1   |  55  |  42  |  5 
Steve   | fake@me.com |  0   |   0  |   0  |  0 
Leon    | josh@me.com |  3   |   0  |   3  |  5 

How in a MySQL query can I get the amount of those message rows that are not开发者_StackOverflow empty or not equal to 0, allowing me to order by that? So it would return

Pez   | 4 Mesasges
Leon  | 3 Messages
Steve | 0 Messages

Im my mind something like:

order by count(!empty(msg1)+!empty(msg2)+!empty(msg3)+!empty(msg4)) 


With normalized tables it could be as simple as

SELECT Count(*) FROM messages WHERE userid=47

But with your schema try something like

SELECT
  name,
  (msg1<>0) + (msg2<>0) + (msg3<>0) + (msg4<>0) as cMessages
FROM
  foo  

edit: Vincent Ramdhanie's answer using if() doesn't rely on MySQL's behaviour to use 0 as false and 1 as true as result of a comparison. I would prefer that.


 select 
     if(msg1 = 0, 0, 1) +
     if(msg2 = 0, 0, 1) +
     if(msg3 = 0, 0, 1) +
     if(msg4 = 0, 0, 1) as NumMsg,Name
 from table


Your best bet would be to normalize your database as follows:

Table users:    (user_id, name, email)
Table messages: (user_id, msg_number, msg_code)

The users table would have user_id as a primary key, while the messages table would have a composite primary key on (user_id, msg_number). The msg_number field would represent the 1-4 message number (the number you represented in your column names).

The composite primary key would guarantee that each user can only have one message for each msg_number. You may also want to create a check constraint so that msg_number is always <= 4. Finally you may want to define user_id in the messages table as a foreign key to the users table.

Note that if a user did not send a message, you should not have a row in the messages table with msg_code = 0. Instead, you should simply omit the row.

With normalized tables, counting the number of messages for each user would be as easy as:

SELECT    u.name, COUNT(m.msg_number) as num_of_messages
FROM      users u
JOIN      messages m ON (m.user_id = u.user_id)
GROUP BY  u.user_id;


As others have said the right way to solve the problem is to normalize your database.

You can get the counts from the current schema - but its a bit messy:

SELECT name, (SIGN(msg1)+SIGN(msg2)+SIGN(msg3)+SIGN(msg4))
FROM yourtable
ORDER BY (SIGN(msg1)+SIGN(msg2)+SIGN(msg3)+SIGN(msg4)) DESC;

C.

0

精彩评论

暂无评论...
验证码 换一张
取 消