sorting mysql table by data within a different table - php

I have to mysql tables and trying to display results of table1 but sorting by table2. For table2 I'm counting all the occurrences of a duplicate id and then display that result descending. Below is as far as I could get and wondering if this can even be done is a single query.
$query = "
SELECT DISTINCT registration.*
FROM registration
INNER JOIN downloads
ON registration.id = downloads.id
GROUP BY downloads.COUNT(id)
ORDER BY downloads.COUNT(id) DESC,
downloads.COUNT(id) DESC
";

I think you want something along these lines:
SELECT Registration.id, Registration.name, Registration.email,
Downloads.document
FROM Registration
JOIN Downloads
ON Downloads.id = Registration.id
JOIN (SELECT id, COUNT(*) as count
FROM Downloads
GROUP BY id) Download_Count
ON Download_Count.id = Registration.id
ORDER BY Download_Count.count DESC
(untested, as it would be nice for the OP to supply sample data and table layouts in the question)

Related

How to sort data selected from one table according to data in another table?

I have tables: post & votes
i want to sort the posts in table 'post' by count of column in table 'votes'.
SELECT * FROM post ORDER BY <SELECT count(*) as c FROM votes WHERE post = $row[srno]>
The 'votes' table contains 2 columns: post and user; It is meant to store votes of each post that exists in 'post' table.
SELECT count(*) as c FROM votes WHERE post = $row[srno]
Above query gives me the no. of votes of the specified post. How do i sort posts by this count?
You can use a JOIN for that:
SELECT p.*, COUNT(*) as vcount
FROM post p
JOIN votes v ON v.post = p.srno
GROUP BY p.*
ORDER BY vcount
This will also add a column vcount to the table that contains the number of votes.
Note that this query will sort in ascending order so lowest number of votes first. You can use DESC to sort in descending order (so highest number of votes first):
SELECT p.*, COUNT(*) as vcount
FROM post p
JOIN votes v ON v.post = p.srno
GROUP BY p.*
ORDER BY vcount DESC
Maybe you can all have from one table, votes:
SELECT COUNT(post) as c, post
FROM votes
GROUP BY Country
ORDER BY post ASC;

Getting data from one table based on results of another SQL PHP

I know this involves JOINS but I can't seem to find a working solution to what I'm trying to do.
I have 2 custom tables :
table1 | table2
---------------------
id id
uid uid
track_id track_id
date date
art active
info
blah
blah2
First I want to select everything WHERE uid=55 AND active=1 from table2 :
$tracks = $wpdb->get_results( "SELECT * FROM table2 WHERE uid = 55 AND active = 1");
And then match the track_id from table2 with results from table1 so I can traverse the table1 data.
I know I can do it like this :
foreach( $tracks as $track ) {
$this_track = $track->track_id;
$results = $wpdb->get_results( "SELECT * FROM table1 WHERE track_id = $this_track");
// Do stuff here
}
But this is the part where it gets tricky...
I then want to ORDER the $results from table1 by date DESC from table2
And this is where I'm lost...
Effectively I want (pseudo code) :
$results = $wpdb->get_results( "SELECT * FROM table1 WHERE track_id = $this_track" ORDER BY date DESC FROM table2);
As well as that last bit, I know I can do this entire routine with JOINS to keep this all in one query and make it way more efficient but I just don't know how.
So just to be clear, my overall routine should be like this :
Get all instances of track_id from table2 where user_id=55 and active=1, then use those results to match the track_id to every result in table1 with the same track_id and then sort the results by date back over from table2
Psuedo code, I know it contains nonsense :
$finalresults = $wpdb->get_results( "SELECT * FROM table2 where uid=55 AND active=1 THEN SELECT * FROM table1 WHERE track_id = "the track_id from the first query" THEN ORDER BY date DESC FROM table2);
Try with this query
SELECT t1.* ,t2.date AS t2date, t2.active FROM table2 AS t2 INNER JOIN table1 AS t1 ON (t1.track_id = t2.track_id) WHERE t2.uid=55 AND t2.active=1 ORDER BY t2.date DESC;
Edit: Explanation of what this query is doing. and inverted the order of the tables retrieved in the query (this don't affect the final datatset, i did this to make to follow the logic of the explanation.
1.- Begin with retrieving all rows from table2 (theres is no specific reason because i used table2 over table1, I'm only following an logical order), using the criteria that you specified iud=55 and active=1
SELECT * FROM table2 WHERE uid=55 AND active=1;
2.- but as you said you need to expand the data retrieved in table2 with some information in table1, that's exactly what it is the directive JOIN made, and we are using INNER JOIN because this type of JOIN will show rows ONLY if data for the uid=55 is present on table1, if there is NO data for the uid=55 present on both TABLES then mysql wil show empty the recordset (0 Rows selected).
in the ON(...) part I specify which criteria mysql will use to compara both tables for match in this case will compare that track_id on table2 it is the same that the specified on table1, if this codition is met then mysql considers it as a match.
anly for convenience and because i'm adding a Second table i gave an Alias to each one t1 and t2.
then the query now seems like this
SELECT * FROM table2 AS t2 INNER JOIN table1 AS t1 ON(t1.track.id = t2.track_id) WHERE t2.uid=55 AND t2.active=1;
3.- but then raise a problem, both tables has rows with the same field names, and this is something that DBMS don't like in their queries, to avoid this situation in the query i only show the fields (id, uid and track_id) from one table in this case t1 (t1.*) and only show the fields that doesn't have this problem from t2 (t2.date AS t2date, t2.active). in this way mysql won't throw any error.
SELECT t1.* ,t2.date AS t2date, t2.active FROM table2 AS t2 INNER JOIN table1 AS t1 ON (t1.track_id = t2.track_id) WHERE t2.uid=55 AND t2.active=1;
4.- for the final step i specify to mysql that i want all found rows ordered descent by a field in the table2;
ORDER BY t2.date DESC;
then this criteria will be applied to the whole selected rows. and the final query has this form.
SELECT t1.* ,t2.date AS t2date, t2.active FROM table2 AS t2 INNER JOIN table1 AS t1 ON (t1.track_id = t2.track_id) WHERE t2.uid=55 AND t2.active=1 ORDER BY t2.date DESC;
if is not completely clear you can ask ...

LIMIT rows from the latest - JOINED tables

I got two tables, customer_ledger and users.
I'm using PHP for my simple log-in program wherein the users input their username and password. Once the account is valid, it will show them their billing history. So I joined the two tables to link the username with the contract number in the other table.
My problem now is, how to display their (5) latest billings based on the field (LDGR_PER_COV_TO)? I created a MySQL query but it gave me a different result.
This is my query:
SELECT
customer_ledger.LDGR_YEAR,
customer_ledger.LDGR_MONTH,
customer_ledger.LDGR_PER_COV_FROM,
customer_ledger.LDGR_PREV_RDNG,
customer_ledger.LDGR_PER_COV_TO,
customer_ledger.LDGR_PRES_RDNG,
customer_ledger.LDGR_KWH_USED,
customer_ledger.LDGR_BILL_AMOUNT
FROM
customer_ledger
INNER JOIN users
ON customer_ledger.LDGR_CONTRACT_NO=users.LDGR_CONTRACT_NO
WHERE users.Username = 'kim'
ORDER BY customer_ledger.LDGR_PER_COV_TO ASC
LIMIT 5
this result will give me rows starting from the top most record. I would like it to display from the bottom-going up (latest record - top record).
Can anyone help?
You should use alises for better readibility,
Then use DESC in place of ASC
SELECT cl.LDGR_YEAR, cl.LDGR_MONTH,
cl.LDGR_PER_COV_FROM, cl.LDGR_PREV_RDNG,
cl.LDGR_PER_COV_TO, cl.LDGR_PRES_RDNG,
cl.LDGR_KWH_USED, cl.LDGR_BILL_AMOUNT
FROM customer_ledger AS cl INNER JOIN users AS u
ON cl.LDGR_CONTRACT_NO=u.LDGR_CONTRACT_NO
WHERE u.Username = 'kim'
ORDER BY cl.LDGR_PER_COV_TO DESC LIMIT 5
New Query ::
SELECT * FROM
(
SELECT cl.LDGR_YEAR, cl.LDGR_MONTH,
cl.LDGR_PER_COV_FROM, cl.LDGR_PREV_RDNG,
cl.LDGR_PER_COV_TO, cl.LDGR_PRES_RDNG,
cl.LDGR_KWH_USED, cl.LDGR_BILL_AMOUNT
FROM customer_ledger AS cl INNER JOIN users AS u
ON cl.LDGR_CONTRACT_NO=u.LDGR_CONTRACT_NO
WHERE u.Username = 'kim'
ORDER BY cl.LDGR_PER_COV_TO DESC LIMIT 5
) AS a
ORDER BY a.LDGR_PER_COV_TO

how to order resultset based on fields from two tables

I have two tables one for topic_likes & one for user_comments.I must get recent updates of like & comment from this tables.Given below is the sql :-
SELECT (required fields...)
LEFT JOIN topic_likes AS TL ON (TL.delete_status=0 AND TL.user_id!=$user_id)
LEFT JOIN user_comments AS UC ON (UC.delete_status=0 AND UC.user_id!=$user_id)
WHERE
(TL.created_date >= '$lastLogin' OR UC.created_date >= '$lastLogin'
ORDER BY UC.created_date desc,TL.created_date desc
LIMIT $limit
I have given order by two fields from two tables(UC.created_date, TL.created_date)
But it does not order the resultset based on created_date from topic_likes.It only orders the results based on user_comments table
But if I removed the limit condition it gives correct results...!!
Any suggestion appreciated
This is a strange approach you're taking. If you want to display user's likes and comments using a single query you should UNION the results. Example:
SELECT * FROM
(
SELECT id, `date`, 'like' as `type` FROM topic_likes
UNION
SELECT id, `date`, 'comment' as `type` FROM user_comments
) a order by a.date DESC limit 5;
The result should be similar to this:
But there are limitations. The number of columns from each subquery must match.

Retrieving count of column mySQL PHP

Hey guys I have a mysql table called interests with 4 columns. interestID, name, categoryID interest_desc and date. the categoryID column is linked to a seperate table. How would I use a mysql query that checked how many interests are in a certain category?
Im guessing i use some sort of count() query?
Thanks guys
Update -
$count_query_v1 = "SELECT categoryID, COUNT(*) AS total FROM interests GROUP by categoryID; "; $answer = mysql_query($count_query_v1) or die(mysql_error()); echo $answer;
Getting closer but still not perfect, i want to echo out the categoryID with the most interestID's
select category_name, count(*) as total
from interests i left join category c on c.category_id = i.category_id
group by i.category_id;
count + group by,
assuming interestID is the unique primary key,
and each interest is tied to single category (as what you have shown)
select categoryID, count(*) as total
from interests
group by categoryID;
// the above example is a simple group by ID without using inner join
output :-
categoryID, total
SELECT COUNT(interestID) FROM interests WHERE categoryID = 'yourvalue';
SELECT COUNT(interestID), categoryID FROM interests GROUP BY categoryID;
Since you are using the insert query each query will insert one record, so just count the number of insert queries you run by using a counter varialble.

Categories