How to get the user with most comments from a table - mysql

I am trying to get the user first name with the most comments. How can I do this?
Here are the tables.
The tables below are the setup for the database tables which I am trying to query.
CREATE TABLE User(
userid varchar(3),
firstname varchar(20),
lastname varchar(20),
age int,
PRIMARY KEY(userid)
)ENGINE=INNODB;
CREATE TABLE Comment(
commentid varchar(3),
userid varchar(3),
eventid varchar(3),
title varchar(20),
comment varchar(50),
PRIMARY KEY(commentid),
FOREIGN KEY(userid) REFERENCES AnonymousUser(userid),
FOREIGN KEY(eventid) REFERENCES Event(eventid)
)ENGINE=INNODB;
INSERT INTO User VALUES('U01','Charles','Darwin',99);
INSERT INTO User VALUES('U02','Keisha','Strawn',24);
INSERT INTO User VALUES('U03','Denise','Malcolm',59);
INSERT INTO User VALUES('U04','Dennis','Stewart',19);
INSERT INTO User VALUES('U05','Robert','Johns',45);
INSERT INTO User VALUES('U06','Marsha','Stewart',33);
INSERT INTO Comment VALUES ('C01','A01','E01','Boring Event','This event was boring');
INSERT INTO Comment VALUES ('C02','A02','E01','Nice Nice Event','This event was Nice');
INSERT INTO Comment VALUES ('C03','A03','E03','Wow','This event was Amazing');
INSERT INTO Comment VALUES ('C04','A01','E01','Very Sad','I missed this event');
The query I tried is
SELECT User.userid FROM User
JOIN comment ON comment.userid = user.userid
WHERE (SELECT COUNT(comment)
FROM comment = (SELECT MAX(userid) FROM comment);

SELECT
userid
FROM
comment
GROUP BY userid
ORDER BY count(userid) DESC
LIMIT 1;
Edit: oh, you need the username. Try this:
SELECT firstname
FROM user
WHERE userid = (
SELECT
userid
FROM
comment
GROUP BY userid
ORDER BY count(userid) DESC
LIMIT 1
);

Query to get firstname with most comments is
select a.firstname, max(a.comment_count) from (
select u.firstname, count(c.commentid) comment_count
from user u join comment c on u.userid = c.userid
group by u.firstname
)a;
That said, I noticed
One of the constraints on table 'comment' is pointing to a table 'AnonymousUser' FOREIGN KEY(userid) REFERENCES AnonymousUser(userid). You have not shared the create table statement for that table.
I had to remove this constraint from table definition in order to successfully create this table in my database
CREATE TABLE Comment(
commentid varchar(3),
userid varchar(3),
eventid varchar(3),
title varchar(20),
comment varchar(50),
PRIMARY KEY(commentid)
);
You dataset for table 'comment' has no userid matching 'user.userid' values
I updated the 'comment' table inserts so I could get some result when executing my query.
INSERT INTO Comment VALUES ('C01','U01','E01','Boring Event','This event was boring');
INSERT INTO Comment VALUES ('C02','U01','E01','Nice Nice Event','This event was Nice');
INSERT INTO Comment VALUES ('C03','U03','E03','Wow','This event was Amazing');
INSERT INTO Comment VALUES ('C04','U06','E01','Very Sad','I missed this event');

Related

inner join gives in mysql gives error code 1052

I created a database with following tables :
CREATE SCHEMA IF NOT EXISTS `facturatiedatabase` ;
USE `facturatiedatabase` ;
DROP TABLE IF EXISTS tblAddress ;
DROP TABLE IF EXISTS tblContact ;
DROP TABLE IF EXISTS tblCustomers ;
CREATE TABLE tblCustomers (
customerID INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
firstname VARCHAR(30) NOT NULL,
lastname VARCHAR(30) NOT NULL,
vat VARCHAR(30) NOT NULL,
customerVisible varchar(1) NOT NULL DEFAULT 'T'
) ENGINE=InnoDB;
CREATE TABLE tblContact (
contactID INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
email VARCHAR(100),
phone VARCHAR(100),
customerID int,
CONSTRAINT FK_customerID_Contact FOREIGN KEY (customerID) REFERENCES tblCustomers(customerID)
) ENGINE=InnoDB;
CREATE TABLE tblAddress (
addressID INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
street VARCHAR(100),
houseNumber VARCHAR(15),
city VARCHAR (100),
country VARCHAR (100),
customerID int,
CONSTRAINT FK_customerID_Adress FOREIGN KEY (customerID) REFERENCES tblCustomers(customerID)
) ENGINE=InnoDB;
INSERT INTO tblCustomers (firstname, lastname,vat)
VALUES ("John","Doe","UV45856855");
INSERT INTO tblContact (customerID,phone, email)
VALUES ((SELECT DISTINCT LAST_INSERT_ID() FROM tblCustomers), "0000001","Johndoe#gmail.com");
INSERT INTO tblAddress (customerID,street,housenumber,city,country)
VALUES ((SELECT DISTINCT LAST_INSERT_ID() FROM tblCustomers), "berkenlaan","1a","Harelbeke","Belgie");
But when i try following inner join it gives me the following error :
LIMIT 0, 1000 Error Code: 1052. Column 'customerID' in field list is ambiguous 0.000 sec.
SELECT customerID, firstname, lastname, vat,email
FROM tblCustomers
INNER JOIN tblContact on tblCustomers.customerID = tblContact.contactID
The error message says it all: the column name customerID is contained in both tables. So which value should mysql select? That is ambiguous, therefore the error.
Have a try with this variant:
SELECT tblCustomers.customerID AS customerID, firstname, lastname, vat,email
FROM tblCustomers
INNER JOIN tblContact on tblCustomers.customerID = tblContact.contactID
(or pick that other tables's column with the same if you need that one...)
And, frankly, I doubt your ON clause is the one you want to use. Shouldn't that be ON tblCustomers.customerID = tblContact.customerID instead?

Read value of a column and assign to another column

MY situation is like this:
I have two tables
TEACHERS and ABSENCES each of them has a column unitid
I want to select the unitid from TEACHERS Table and insert into ABSENCES table.
EDIT:
Can this be added into this query: ("insert into absences (student_id, date) values ('".$_GET['student_id']."','".date('Y-m-d H:i:s')."')");
?
try this
INSERT INTO ABSENCES(unitid) select unitid from TEACHERS
I tried to depict your scenario as below
Create Absence Table
create table absence (absence_id int not null auto_increment primary key,
`date` datetime, `subject` varchar(20),
unit_session varchar(20), unitid int);
Insert Data to Absence Table
insert into absence(`date`, `subject`, unit_session)
values(now(),'Math','first'),(now(),'Biology','second'),(now(),'Physics','third')
Create and insert data to Teachers table
create table teachers (username varchar(10), `password` varchar(10), unitid int);
insert into teachers values('abcdsed','fgdfgfdfgd',23),
('abcdced','fgdfgrtfgd',3),('harikas','fgdfgfdfgd',23);
At this point as you can see, Absence Table don't have any value for unitid column. it's NULL.
Create a temporary table as below
create temporary table temptest(id int not null auto_increment primary key,
unit_id int);
Insert unitid from Teachers to temporary table
insert into temptest(unit_id) select unitid from teachers
Now finally, update Absence table by joining with temporary table like below
UPDATE absence a
JOIN temptest b
ON a.absence_id = b.id
SET a.unitid = b.unit_id

MySQL Prepared Statement table 3th

I am not able to get data using the join query with 3Th table.
Table p:
- id
- name
Table s:
- id
- name
- description
Table ps:
- p_id
- s_id
$stmt = $this->conn->prepare("SELECT p.id, p.name FROM p, ps WHERE p.id = 1 AND ps.p_id = 1 AND ps.s_id = 1");
Here's the error: Call to a member function execute() on a non-object
Thanks
Two question:
(1) Have you tried running your query directly from the MySQL command line? And if so does it give you your desired result?
(2) Could you show more of your code. Perhaps the problem located some where else in your code.
For a start try this explicit JOIN query:
SELECT p.id, p.name
FROM p
JOIN ps
ON p.id = ps.p_id
JOIN s
ON ps.s_id = s.id
WHERE s.id = 1;
Sample data:
CREATE TABLE p
(
id int auto_increment primary key,
name varchar(20)
)ENGINE=InnoDB;
INSERT INTO p
(name)
VALUES
('Bob'),
('Jack'),
('John');
CREATE TABLE s
(
id int auto_increment primary key,
name varchar(30)
)ENGINE=InnoDB;
INSERT INTO s
(name)
VALUES
('blablabla'),
('Foo'),
('Foobar');
CREATE TABLE ps
(
id int auto_increment primary key,
p_id int,
s_id int,
FOREIGN KEY (p_id) REFERENCES p(id),
FOREIGN KEY (s_id) REFERENCES s(id)
)ENGINE=InnoDB;
INSERT INTO ps
(p_id,s_id)
VALUES
(1,1),
(1,2),
(2,1),
(2,2),
(3,2);
SQLFiddle demo

insert child mysql

I've got a newbie question...
I've got two tables:
parentTable
-----------
id_user int(11) not null auto increment primary key,
email varchar(64),
pass varchar(64)
childTable
----------
id_user int(11) not null,
name varchar(64),
address varchar(512),
foreign key (id_user) references parentTable(id_user)
on update cascade
on delete restrict
Now can I insert:
insert into childTable (id_user) select id_user from parentTable where id_user = '1'
But I just want to insert also name and address values.
Sorry for the newbie question, but I lurked for a day and found nothing.
Thank you in advance for your reply.
The interesting part about your query is that you know the id_user you're trying to select to insert - it's in your WHERE clause.
If you will always know the id_user, you can skip the extra SELECT portion of the query and directly do:
INSERT INTO childTable (id_user, name, address) VALUES (1, 'some name', '123 test street');
If you, for some other reason, need the additional SELECT, you can append the name/address values directly into the field-list, like this:
INSERT INTO childTable (id_user, name, address)
SELECT id_user, 'some name', '123 test street' FROM parentTable WHERE id_user = '1';

Oracle table with only current records; reduce duplicates using max(date)

I need to create a new table in oracle with only the most current date for each record (step 1), and calculate days between (step 2).
Your suggestions are greatly appreciated:)))
Step 1: First I need to find the max (Mod_date) for each record from table USERS.
TABLE: USERS
Name................Mod_Date
Jason Martin....... 25-JUL-89
Al Mathews......... 21-MAR-89
James Smith........ 12-DEC-88
Robert Black....... 15-JAN-84
Jason Martin....... 25-JUL-99
Al Mathews......... 21-MAR-96
James Smith........ 12-DEC-98
Robert Black....... 15-JAN-94
*TABLE_DESIRED_RESULTS_step1
Name............... Max(Mod_Date)
Jason Martin....... 25-JUL-99
Al Mathews......... 21-MAR-96
James Smith........12-DEC-98
Robert Black.......15-JAN-94
Step 2: Calculate “Number of Days Between Regist_Date and Mod_Date” & add it to the table.
TABLE: REGISTRATION
Name................Regist_Date
Jason Martin.........20-JUL-99
Al Mathews...........23-MAR-96
Robert Black.........20-JAN-94
*TABLE_DESIRED_RESULTS_step2
Name...............Max(Mod_Date).....Number of Days Between Regist_Date and Mod_Date
Jason Martin...... 25-JUL-99..........5
Al Mathews........ 21-MAR-96.........-2
James Smith....... 12-DEC-98..........null
Robert Black...... 15-JAN-94..........-5
*Please note, this data is made up and I already have existing unions and joins to which I have to add this logic. Thanks and have a nice day!
here is my updated answer with a sample.
The important thing is that your date column have the DATE type.
Here is the tables and data following your specification.
CREATE TABLE USERS
(
ID_USER NUMBER(6) NOT NULL,
NAME VARCHAR2(64) NOT NULL,
MOD_DATE DATE NOT NULL,
CONSTRAINT PK_user PRIMARY KEY (ID_USER)
) ;
INSERT INTO USERS VALUES (1,'Jason Martin',TO_DATE('25-07-1989','DD-MM-YYYY'));
INSERT INTO USERS VALUES (2,'Al Mathews',TO_DATE('21-03-1989','DD-MM-YYYY'));
INSERT INTO USERS VALUES (3,'James Smith',TO_DATE('12-12-1988','DD-MM-YYYY'));
INSERT INTO USERS VALUES (4,'Robert Black',TO_DATE('15-01-1984','DD-MM-YYYY'));
INSERT INTO USERS VALUES (5,'Jason Martin',TO_DATE('25-07-1999','DD-MM-YYYY'));
INSERT INTO USERS VALUES (6,'Al Mathews',TO_DATE('21-03-1996','DD-MM-YYYY'));
INSERT INTO USERS VALUES (7,'James Smith',TO_DATE('12-12-1998','DD-MM-YYYY'));
INSERT INTO USERS VALUES (8,'Robert Black',TO_DATE('15-01-1994','DD-MM-YYYY'));
CREATE TABLE REGISTRATION
(
ID_REG NUMBER(6) NOT NULL,
NAME VARCHAR2(64) NOT NULL,
REGIST_DATE DATE NOT NULL,
CONSTRAINT PK_reg PRIMARY KEY (ID_REG)
) ;
INSERT INTO REGISTRATION VALUES (1,'Jason Martin',TO_DATE('20-07-1999','DD-MM-YYYY'));
INSERT INTO REGISTRATION VALUES (2,'Al Mathews',TO_DATE('23-03-1996','DD-MM-YYYY'));
INSERT INTO REGISTRATION VALUES (3,'Robert Black',TO_DATE('20-01-1994','DD-MM-YYYY'));
First step
CREATE TABLE TABLE_DESIRED_RESULTS_step1
AS (
SELECT
u.NAME
, max(u.MOD_DATE) as "maxi"
FROM USERS u
GROUP BY u.NAME);
second step
CREATE TABLE TABLE_DESIRED_RESULTS_step2
AS (
SELECT
t.NAME
,t."maxi"
, (t."maxi" - r.REGIST_DATE ) as "Nbdays bw RegD and Mod_D"
FROM TABLE_DESIRED_RESULTS_step1 t LEFT OUTER JOIN REGISTRATION r
ON t.NAME = r.NAME);
The trick here is that LEFT OUTER JOIN allows null value if there is no match with the join.
But there is a database design concern for me.
If you have 2 users with the exact same name , you will merge 2 persons in one.
Here a solution using IDs and doing the join on the IDs.
CREATE TABLE USERS
(
ID_USER NUMBER(6) NOT NULL,
NAME VARCHAR2(64) NOT NULL,
CONSTRAINT PK_user PRIMARY KEY (ID_USER)
) ;
CREATE TABLE MOD_USERS
(
ID_MOD NUMBER(6) NOT NULL,
ID_USER NUMBER(6) NOT NULL,
CONSTRAINT PK_usermod PRIMARY KEY (ID_MOD)
) ;
ALTER TABLE MOD_USERS ADD (
CONSTRAINT FK_user_mod
FOREIGN KEY (ID_USER)
REFERENCES USERS (ID_USER));
CREATE TABLE REGISTRATION
(
ID_REG NUMBER(6) NOT NULL,
ID_USER VARCHAR2(64) NOT NULL,
REGIST_DATE DATE NOT NULL,
CONSTRAINT PK_reg PRIMARY KEY (ID_REG)
) ;
ALTER TABLE REGISTRATION ADD (
CONSTRAINT FK_user_reg
FOREIGN KEY (ID_USER)
REFERENCES USERS (ID_USER))
;
First step
CREATE TABLE TABLE_DESIRED_RESULTS_step1
AS (
SELECT
m.ID_USER , u.NAME
, max(u.MOD_DATE) as "maxi"
FROM USERS u INNER JOIN MOD_USERS m
ON u.ID_USER = m.ID_USER
GROUP BY m.ID_USER , u.NAME);
second step
CREATE TABLE TABLE_DESIRED_RESULTS_step2
AS (
SELECT
t.ID_USER , t.NAME
,t."maxi"
, (t."maxi" - r.REGIST_DATE ) as "Nbdays bw RegD and Mod_D"
FROM TABLE_DESIRED_RESULTS_step1 t LEFT OUTER JOIN REGISTRATION r
ON t.ID_USER = r.ID_USER);