Null result while use and operator in MYSQL IN - php
This is my query to get filter data from user table where category will fetch from another table.
SELECT * FROM jobfia_users
WHERE country_id='4'
and user_id IN (SELECT worker_id
FROM jobfia_worker_skills
WHERE skill_id = '42'
)
This is not giving any error, but not return any row also.
while there are lots of records are available in table using this filter.
Can any one help please ?
Additionally to the quotes surrounding your INT ids, your query will be better expressed like this :
SELECT u.*
FROM jobfia_users u
INNER JOIN jobfia_worker_skills ws
ON ws.worker_id=u.user_id AND ws.skill_id = 42
WHERE u.country_id=4
If your country_id and skill_id are int type, remove ' around values.
SELECT * FROM jobfia_users
WHERE country_id=4
and user_id IN (SELECT worker_id
FROM jobfia_worker_skills
WHERE skill_id = 42
)
Tested your code with and without '' and it works. Make sure you have data and you did not misspell some column name.
Maybe you have collision of some column names. Try to use this syntax:
\`table_name\`.\`column_name\`
Code:
SELECT *
FROM `jobfia_users`
WHERE `jobfia_users`.`country_id`='4'
AND `jobfia_users`.`user_id` IN (SELECT `jobfia_worker_skills`.`worker_id`
FROM `jobfia_worker_skills`
WHERE `jobfia_worker_skills`.`skill_id` = '42')
Related
Which Clause to use instead of IN Clause in MYSQL
My Question is Which Clause use instead of IN Clause in MYSQL with PHP Because IN Clause Limit 1024 character. My Character limit exceed to 1024 character. SELECT * FROM TblUser WHERE Status != 'Deleted' AND UserId IN (0,10,11,12,13,14,15,22,45,114,144,155,156,167,211,439,440,441,443,445,450,455,456,457,458,459,1111,1154,1156,1165,1451,1541,11111,11112,11113,11114,11115,11116,11117,11118,11119,11656,15451,16561,17671,18781,33131,33311,33411,54511,111110,111111,111112,111113,111114,111115,111116,111117,111118,111119,111120,111121,111122,111123,111124,111125,111126,111127,111128,111129,111130,111131,111132,111133,111134,111135,111136,111137,111138,111139,111140,111141,111142,111143,111144,111145,111146,111147,111148,111149,111150,111151,111152,111153,111154,111155,111156,111157,111158,111159,111160,111161,111162,111163,111164,111165,111166,111167,111168,111169,111170,111171,111172,111173,111174,111175,111176,111177,111178,111179,111180,111181,111182,111183,111184,111185,111186,111187,111188,111189,111190,111191,111192,111193,111194,111195,111196,111197,111198,111199,1111100,11112101,11112102,11112103,11112104,11112105,11112106,11112107,11112108,11112109,11112110,11112111,11112112,11112113,11112114,11112115,11112116,11112117,11112118,11112119,11112120,11112121,11112122,11112123,11112124,11112125,11112126,11112127,11112128,11112129,11112130,11112131,11112132,11112133,11112134,11112135,11112136,11112137,11112138,11112139,11112140,11112141,11112142,11112143,11112144,11112145,11112146,11112147,11112148,11112149,11112150,11112151,11112152,11112153,11112154,11112155,11112156,11112157,11112158,11112159,11112160,11112161,11112162,11112163,11112164,11112165,11112166,11112167,11112168,11112169,11112170,11112171,11112172,11112173,11112174,11112175,11112176,11112177,11112178,11112179,11112180,11112181,11112182,11112183,11112184,11112185,11112186,11112187,11112188,11112189,11112190,11112191,11112192,11112193,11112194,11112195,11112196,11112197,11112198,11112199,11112200); Please help Which Clause use instead of IN Clause in MYSQL with PHP?
Is the list of values that are used in the IN statement always the same, or is that list the result of some other query? If the latter is the case, you could use that query as a subquery: SELECT * FROM tbluser WHERE status != 'Deleted' AND userid IN ( SELECT userid FROM sometable WHERE ... )
Yes you are limited within an IN statement, one thing you could do is create a temporary table which stores the values. CREATE TEMPORARY TABLE IF NOT EXISTS temp AS (SELECT userid FROM tbluser); In PHP create your INSERT INTO script: $str = '0,10,11,12,13,14,15,22,45,114,144,155,156,167,211,439,440,441,443,445,450,455,456,457,458,459,1111,1154,1156,1165,1451,1541,11111,11112,11113,11114,11115,11116,11117,11118,11119,11656,15451,16561,17671,18781,33131,33311,33411,54511,111110,111111,111112,111113,111114,111115,111116,111117,111118,111119,111120,111121,111122,111123,111124,111125,111126,111127,111128,111129,111130,111131,111132,111133,111134,111135,111136,111137,111138,111139,111140,111141,111142,111143,111144,111145,111146,111147,111148,111149,111150,111151,111152,111153,111154,111155,111156,111157,111158,111159,111160,111161,111162,111163,111164,111165,111166,111167,111168,111169,111170,111171,111172,111173,111174,111175,111176,111177,111178,111179,111180,111181,111182,111183,111184,111185,111186,111187,111188,111189,111190,111191,111192,111193,111194,111195,111196,111197,111198,111199,1111100,11112101,11112102,11112103,11112104,11112105,11112106,11112107,11112108,11112109,11112110,11112111,11112112,11112113,11112114,11112115,11112116,11112117,11112118,11112119,11112120,11112121,11112122,11112123,11112124,11112125,11112126,11112127,11112128,11112129,11112130,11112131,11112132,11112133,11112134,11112135,11112136,11112137,11112138,11112139,11112140,11112141,11112142,11112143,11112144,11112145,11112146,11112147,11112148,11112149,11112150,11112151,11112152,11112153,11112154,11112155,11112156,11112157,11112158,11112159,11112160,11112161,11112162,11112163,11112164,11112165,11112166,11112167,11112168,11112169,11112170,11112171,11112172,11112173,11112174,11112175,11112176,11112177,11112178,11112179,11112180,11112181,11112182,11112183,11112184,11112185,11112186,11112187,11112188,11112189,11112190,11112191,11112192,11112193,11112194,11112195,11112196,11112197,11112198,11112199,11112200'; $ids = explode(',', $str); foreach ($ids as $value){ echo 'INSERT INTO temp VALUES(' . $value . '); </br>'; } But change the echo for the mysqli query. Then: SELECT * FROM tbluser u where status !='Deleted' And exists(select * from temp u1 where u1.userid = u.userid) Or you can do an inner join temp u1 on u1.userid = u.userid
#Abid as you mentioned your question in this case #Guss is right. What i am thinking if values mentioned IN clause comes from GROUP_CONCAT then might be possible duplicate values exist with comma seperated. So to remove duplicacy we can use DISTINCT. For example : SELECT GROUP_CONCAT(UserId) FROM sometable Above query can give duplicate values. SELECT GROUP_CONCAT(DISTINCT UserId) FROM sometable SELECT t1.UserRoleId, t1.EntityId, GROUP_CONCAT( DISTINCT t1.PermissionId ) AS Permissions FROM userpermission t1, bill_companies t2 WHERE t1.Status = 'Active' AND t2.status = 'Active' AND UserGroupId IN ( 84, 85, 86 ) LIMIT 0 , 30 Above query gives you userid's without duplicacy. This can also reduce the size of comma seperated ids. Hope this will help.
You could create groups using php if there are Ids which follow by increment e. g. 1,2,3 and replace them by a OR (id >= 1 AND id <= 3) Alternative approach: Search Max and Min ID in your List and query using an interval (greater than and less than) and use php to do the job.
If you really want to avoid using IN then you could use FIND_IN_SET():- SELECT * FROM TblUser WHERE Status != 'Deleted' AND FIND_IN_SET(UserId, '0,10,11,12,13,14,15,22,45,114,144,155,156,167,211,439,440,441,443,445,450,455,456,457,458,459,1111,1154,1156,1165,1451,1541,11111,11112,11113,11114,11115,11116,11117,11118,11119,11656,15451,16561,17671,18781,33131,33311,33411,54511,111110,111111,111112,111113,111114,111115,111116,111117,111118,111119,111120,111121,111122,111123,111124,111125,111126,111127,111128,111129,111130,111131,111132,111133,111134,111135,111136,111137,111138,111139,111140,111141,111142,111143,111144,111145,111146,111147,111148,111149,111150,111151,111152,111153,111154,111155,111156,111157,111158,111159,111160,111161,111162,111163,111164,111165,111166,111167,111168,111169,111170,111171,111172,111173,111174,111175,111176,111177,111178,111179,111180,111181,111182,111183,111184,111185,111186,111187,111188,111189,111190,111191,111192,111193,111194,111195,111196,111197,111198,111199,1111100,11112101,11112102,11112103,11112104,11112105,11112106,11112107,11112108,11112109,11112110,11112111,11112112,11112113,11112114,11112115,11112116,11112117,11112118,11112119,11112120,11112121,11112122,11112123,11112124,11112125,11112126,11112127,11112128,11112129,11112130,11112131,11112132,11112133,11112134,11112135,11112136,11112137,11112138,11112139,11112140,11112141,11112142,11112143,11112144,11112145,11112146,11112147,11112148,11112149,11112150,11112151,11112152,11112153,11112154,11112155,11112156,11112157,11112158,11112159,11112160,11112161,11112162,11112163,11112164,11112165,11112166,11112167,11112168,11112169,11112170,11112171,11112172,11112173,11112174,11112175,11112176,11112177,11112178,11112179,11112180,11112181,11112182,11112183,11112184,11112185,11112186,11112187,11112188,11112189,11112190,11112191,11112192,11112193,11112194,11112195,11112196,11112197,11112198,11112199,11112200') However the only limit for the number of entries in an IN clause is set by max_allowed_packet (as others have stated) and the same restriction would apply to this. max_allowed_packet
Mysql query "WHERE 2 IN (`column`)" not working
I want to execute a query where I can find one ID in a list of ID. table user id_user | name | id_site ------------------------- 1 | james | 1, 2, 3 1 | brad | 1, 3 1 | suko | 4, 5 and my query (doesn't work) SELECT * FROM `user` WHERE 3 IN (`id_site`) This query work (but doesn't do the job) SELECT * FROM `user` WHERE 3 IN (1, 2, 3, 4, 6)
That's not how IN works. I can't be bothered to explain why, just read the docs Try this: SELECT * FROM `user` WHERE FIND_IN_SET(3,`id_site`) Note that this requires your data to be 1,2,3, 1,3 and 4,5 (ie no spaces). If this is not an option, try: SELECT * FROM `user` WHERE FIND_IN_SET(3,REPLACE(`id_site`,' ','')) Alternatively, consider restructuring your database. Namely: CREATE TABLE `user_site_links` ( `id_user` INT UNSIGNED NOT NULL, `id_site` INT UNSIGNED NOT NULL, PRIMARY KEY (`user_id`,`site_id`) ); INSERT INTO `user_site_links` VALUES (1,1), (1,2), (1,3), (2,1), (2,3), (3,4), (3,5); SELECT * FROM `user` JOIN `user_site_links` USING (`id_user`) WHERE `id_site` = 3;
Try this: FIND_IN_SET(str,strlist)
NO! For relation databases Your table doesn't comfort first normal form ("each attribute contains only atomic values, and the value of each attribute contains only a single value from that domain") of a database and you: use string field to contain numbers store multiple values in one field To work with field like this you would have to use FIND_IN_SET() or store data like ,1,2,3, (note colons or semicolons or other separator in the beginning and in the end) and use LIKE "%,7,%" to work in every case. This way it's not possible to use indexes[1][2]. Use relation table to do this: CREATE TABLE user_on_sites( user_id INT, site_id INT, PRIMARY KEY (user_id, site_id), INDEX (user_id), INDEX (site_id) ); And join tables: SELECT u.id, u.name, uos.site_id FROM user_on_sites AS uos INNER JOIN user AS u ON uos.user_id = user.id WHERE uos.site_id = 3; This way you can search efficiently using indexes.
The problem is that you are searching within several lists. You need something more like: SELECT * FROM `user` WHERE id_site LIKE '%3%'; However, that will also select 33, 333 and 345 so you want some more advanced text parsing.
The WHERE IN clause is useful to replace many OR conditions. For exemple SELECT * FROM `user` WHERE id IN (1,2,3,4) is cleaner than SELECT * FROM `user` WHERE id=1 OR id=2 OR id=3 OR id=4 You're just trying to use it in a wrong way. Correct way : WHERE `field` IN (list_item1, list_item2 [, list_itemX])
Get one value when cell input is same
I would like to get one value instead of all values when they have the same name. within an sql query. Im using fullcalendar. and have two tables one for the events(evenement) and one for the receiver(evenementontvanger). evenementontvanger: id idEvent 1 231 2 231 3 231 evenement: id title 231 hello I would like to show only one title not 3 my sql query: "SELECT * FROM `evenement` JOIN `evenementontvanger` ON `evenementontvanger`.`idEvent` = `evenement`.`id` WHERE `idEvent` = `evenement`.`id`"
You can use distinct to do so as SELECT distinct `evenementontvanger`.`idEvent`,`evenement`.`title` FROM `evenement` JOIN `evenementontvanger` ON `evenementontvanger`.`idEvent` = `evenement`.`id` WHERE `idEvent` = `evenement`.`id`; How ever the above will not bother about idWerknemer and if you want to display them as group use Group_concat as SELECT `evenementontvanger`.`idEvent`, `evenement`.`title`, group_concat(`evenementontvanger`.`idWerknemer`) as `idWerknemer` FROM `evenement` JOIN `evenementontvanger` ON `evenementontvanger`.`idEvent` = `evenement`.`id` WHERE `idEvent` = `evenement`.`id` Group By `evenementontvanger`.`idEvent` Check the demo here http://sqlfiddle.com/#!2/290b4/13
Use SELECT DISTINCT on your query to eliminate duplicates : The ALL and DISTINCT options specify whether duplicate rows should be returned. ALL (the default) specifies that all matching rows should be returned, including duplicates. DISTINCT specifies removal of duplicate rows from the result set. It is an error to specify both options. DISTINCTROW is a synonym for DISTINCT. From MySQL docs
use either top 1 OR select distinct
trying to output the correct value from SQL query from comparing a different table
I'm very new with SQL and need assistance on how I can accomplish this task using the correct query. I have 2 tables that I need to use. Table "TB1" has: id Name 1 bob 2 blow 3 joe table "TB2" has: compid property 1 bob 2 blow I am trying to get which compid is missing in "TB2" and insert it from "TB1" the query I am doing is: SELECT id, name from TB1, TB2 where id <> compid what I get is 2 ouputs of Id 1, and 2, and 3 outputs from id 3. by using php: for($i=0;$i <= mysql_num_rows($comp)-1; $i++) { echo mysql_result($comp, $i, 0)."<br>"; } and I expected the ouput 3 but instead got this: 1 1 2 2 3 3 3 I understand its comparing all the rows within the table but is there a way to achieve what I am looking for? Thanks for your time.
You are performing an implicit Cartesian JOIN which results in every row against every other row. You need to specify what attribute JOINs the two tables. Using implicit syntax (not recommended): SELECT id, name FROM TB1, TB2 WHERE id <> compid AND TB1.Name = TB2.property <-- Column join Using explicit syntax: SELECT id, name FROM TB1 JOIN TB2 ON TB2.property = TB1.Name <-- Column join WHERE id <> compid To accomplish your goal you would need something along the lines of: SELECT TB1.id, TB1.name FROM TB1 LEFT JOIN TB2 ON TB2.property = TB1.Name WHERE TB2.compid IS NULL See it in action It's best practice to always alias the columns you select to prevent ambiguity.
To select it you can do: SELECT * FROM TB1 WHERE id NOT IN ( SELECT compid FROM TB2 );
Joining two tables but the join key is in a query string
I want to join these two table but the join key of the second table is in a query string, page table, page_id url 1 a 2 c 3 d system table, system_id query 1 page_id=1&content=on&image=on 2 type=post&page_id=2&content=on as you can see that page_id is part of the query string in system table. so how can I join them like the standard joining table method below? SELECT* FROM page AS p LEFT JOIN system AS s ON p.page_id = s.page_id EDIT: I def can change the system table into something like this, system_id page_id query 1 1 page_id=1&content=on&image=on 2 2 type=post&page_id=2&content=on 3 NULL type=page But the reason why I don't want to do this is that the page_id is no need for many certain records. I don't want make a column with too many null.
I would definitely create columns for page_id,content, image and type (and get them indexed). Then the database would be much lighter and would work much faster.
Joining two tables without the common field and data type, is fundamentally wrong IMO. I will suggest that you extract the page_id and insert it in the database and use a normal join to accomplish what you are searching for. SO making the columns like +------------+-----------+---------+ | system_id | page_id | query | ------------------------------------ Here is a snippet with which you are extract the page_id. $query = 'page_id=1&content=on&image=on'; $queryParts = explode('&', $query); $params = array(); foreach ($queryParts as $param) { $item = explode('=', $param); $params[$item[0]] = $item[1]; } $page_id = $parems['page_id']; Then you can go on with the insert and use simple join statement to solve your problem in a proper way. Update: Since you are able to change the schema to a feasible one. You dont need to worry about some rows having empty rows on this.
I guess you wanted something like this (MSSQL!): DECLARE #query VARCHAR(50) DECLARE #Lenght INT DECLARE #PageID INT SET #query = '4kkhknmnkpage_id=231&content=on&image=on' SET #Lenght = PATINDEX('%&%', substring(#query,PATINDEX('%page_id=%', #query),50)) - 9 SET #PageID = CAST(SUBSTRING(#query,PATINDEX('%page_id=%', #query) + 8,#Lenght) AS INT) SELECT #PageID -- you can do as you please now :) OR: SELECT* FROM page AS p LEFT JOIN (SELECT CAST(SUBSTRING(query,PATINDEX('%page_id=%', query) + 8,(PATINDEX('%&%', substring(query,PATINDEX('%page_id=%', query),50)) - 9)) AS INT) AS page_id FROM system) AS s ON p.page_id = s.page_id -- Do as you please again :) I guess what you really wanted was something like this (MYSQL!): SET #query := '4kkhknmnkpage_id=231&content=on&image=on'; SET #Lenght := POSITION('&' IN (SUBSTR(#query,POSITION('page_id=' IN #query),50))) - 9; SET #PageID := CAST(SUBSTR(#query,POSITION('page_id=' IN #query) + 8,#Lenght) AS SIGNED ); SELECT #PageID OR SELECT* FROM page AS p LEFT JOIN (SELECT CAST(SUBSTR(query,POSITION('page_id=' IN query) + 8,(POSITION('&' IN (SUBSTR(query,POSITION('page_id=' IN query),50))) - 9)) AS SIGNED) AS pageID FROM system) AS s ON p.page_id = s.pageID