Mysql: Order by like? - mysql

assume that we are performing search using keywords: keyword1, keyword2, keyword3
there are records in database with column "name":
1: John Doe
2: Samuel Doe
3: John Smith
4: Anna Smith
now Query:
SELECT * FROM users WHERE (name LIKE "%John%" OR name LIKE "%Doe%")
it will select records: 1,2,3 (in this order)
but i want to order it by keyword
in example keyword1=John, keyword2=Doe
so it should be listed by keywords: 1,3,2 (because i want to perform search for "Doe" after searching for "John")
I was thinking about SELECT DISTINCT FROM (...... UNION .....)
but it will be much easier to order it somehow in another way (real query is really long)
are there any tricks to create such order?

order by case
when name LIKE "%John%" then 1
when name LIKE "%Doe%" then 2
else 3
end

To build on RedFilter's answer, you could make the rows that have both keywords to be at the top:
order by case
when (name LIKE "%John%" and name LIKE "%Doe%") then 1
when name LIKE "%John%" then 2
when name LIKE "%Doe%" then 3
end

Read up on Boolean Fulltext Searches, with which you can do ordering.

SELECT *
from
(
SELECT u.*, 1 OrderNum
FROM users
WHERE (name LIKE "%John%")
UNION
SELECT u.*, 2 OrderNum
FROM users
WHERE (name LIKE "%Doe%")
)
Order by OrderNum

My example will Order all of the John's Alphabetically followed by the Doe's.
ORDER BY CASE
WHEN name LIKE "John%Doe" THEN CONCAT('a',name)
WHEN name LIKE "John%" THEN CONCAT('b',name)
WHEN name LIKE "%Doe" THEN CONCAT('c',name)
ELSE name
END

Related

Define a custom ORDER BY order in mySQL using the LIKE word

How can I make a custom order where I sort the rows by NAME where the first rows' name has Bob in it followed by rows with name of Alex in it?
To explain what exactly I mean: I have made the following query to sort result if NAME = 'Bob' and if NAME = 'Alex':
SELECT * FROM table
ORDER BY CASE `NAME`
WHEN 'Bob' THEN 1
WHEN 'Alex' THEN 2
ELSE 3
END
But this only works when the NAME is exactly equal to Bob or Alex. I want to modify it to sort if the NAME has Bob or Alex in it, essentially if NAME LIKE '%Bob%' and NAME LIKE '%Alex%'. I tried something like the following but it does not work.
ORDER BY CASE `NAME`
WHEN LIKE '%Bob%' THEN 1
WHEN LIKE '%Alex%' THEN 2
ELSE 3
END
What is the correct syntax for this?
Use the other form of CASE where you specify a condition in WHEN rather than a value.
ORDER BY CASE
WHEN NAME LIKE '%Bob%' THEN 1
WHEN NAME LIKE '%Alex%' THEN 2
ELSE 3
END

How can I select to like wildcards in mysql

I have a table which has column name and having stored
|name|
Lebron James C. Durant
And I want to select and filter incomplete name. But the result is null.
SELECT * from partners where name LIKE "%Lebron James Durant%"
Here's my expected result in this query.
|name|
Lebron James C. Durant
Replace spaces with % signs.
SELECT * from partners where name LIKE '%Lebron%James%Durant%';
If you want to query an arbitrary string, use like this (#n may be your query parameter):
SET #n = 'Lebron James Durant';
SELECT * from partners where name LIKE CONCAT('%', REPLACE(#n, ' ', '%'), '%')

What will be Mysql query for group by and order by dictionary style?

Trying to fetch data and print as like dictionary.
Table:
blog_tags
id name
1 atag1
2 atag2
3 dtag1
4 etag1
5 etag2
6 ctag1
7 ctag2
8 ctag3
9 ztag1
I want the data output as:
A
atag1
atag2
C
ctag1
ctag2
D
dtag1
E
etag1
etag2
Z
ztag1
Started with this:
select name from blog_tags order by name;
what will be mysql query for this?
Try something like this
select name
from (
select distinct upper(substring(name, 1, 1)) as name
from blog_tags
union all
select name
from blog_tags
)
order by name
Edit
If you want to get raw data for application level manipulation, I would suggest querying the db this way
select upper(substring(name, 1, 1)) as key,
name
from blog_tags
order by 1, 2
You can use the bellow query to achieve this as given below
select substr(name,1,1),group_conact(name) from blog_tags group by substr(name,1,1);
This query will group the name's by first character and will group concat the name's as comma separated. You can convert the result from your programming language to array
The output will be like given below
substr(name,1,1) group_conact(name)
A atag1,atag2
C ctag1,ctag2

mysql regexp for all column with same data

i have a table like this.
id name father_name age
1 raja first 12
2 second first 13
When i execute a below query.
SELECT * FROM class WHERE name REGEXP 'first|12'
OR father_name REGEXP 'first|12'
OR age REGEXP 'first|12'
I getting below as a results.
id name father_name age
1 raja first 12
2 second first 13
But I want below as a result.
id name father_name age
1 raja first 12
If I change name with or condition. I can achieve.But
As same time the user given raja|12 means
SELECT * FROM class WHERE name REGEXP 'raja|12'
OR father_name REGEXP 'raja|12'
OR age REGEXP 'raja|12'
I want the result like this.
id name father_name age
1 raja first 12
Because i dont know which one will get from user name or father_name or age or all the three. So if i get all the three there is no problem. But when i get a singl or doble values so i need to search regarding that.
Is there any possibility to get those results?
You seem to want and instead of or, but this is complicated by the fact that you don't seem to care about name. I'm tempted to say:
SELECT *
FROM class
WHERE father_name REGEXP 'first|12' AND
age REGEXP 'first|12';
I'm not sure what name is doing in the WHERE clause.
EDIT:
It occurs to me that you want the best matching row. If so:
SELECT *
FROM class
WHERE name REGEXP 'first|12' OR
father_name REGEXP 'first|12' OR
age REGEXP 'first|12'
ORDER BY ((name REGEXP 'first|12') + (father_name REGEXP 'first|12') + (age REGEXP 'first|12')) DESC
LIMIT 1;
Please be aware that REGEXP 'xx|yy' means this matches xx OR yy so your result is correct for that query.
To get the result you want, you will have to clarify what you want to achieve. I assume you want the follwing: select all rows where the father is first AND age is 12
You can achieve this by using:
SELECT * FROM mytable WHERE father_name like 'first' AND age = 12;
You can try this solution here: Relevant SqlFiddle.
Edit1: Possible alternative soultion after more comments by OP:
SELECT * FROM mytable WHERE
father_name IN ('first', '12') AND age IN ('first', '12')
OR
father_name IN ('first', '12') AND name IN ('first', '12')
OR
name IN ('first', '12') AND age IN ('first', '12');
You can try this solution here: Relevant SqlFiddle.

sort particular rows using mysql order case

I have a table with incremented id from 1,2,3...and so on. What i want is just to sort the data in descending order on the basis of field 'id' except first two rows. I tried using below query:-
SELECT * FROM categories ORDER BY CASE WHEN id<3 THEN 0 ELSE id END DESC
It give me the result like
id name
5 Meal
4 Apparel
3 Electronics
1 Sports
2 Lifestyle
But output should come like
id name
1 Sports
2 Lifestyle
5 Meal
4 Apparel
3 Electronics
Is there any way to achieve this by using such query?
Try this:
SELECT *
FROM categories
ORDER BY CASE WHEN id < 3 THEN 10000 - id ELSE id END DESC;
-- ----------------------------^
-- use a very large number
Edit:
A better solution which does not require hard coding 10000:
SELECT *
FROM categories
ORDER BY CASE WHEN id < 3 THEN id ELSE 3 END, id DESC
-- ---------------------^ ^
-- ------------------------------------|
-- these numbers must be same
Change it to:
CASE WHEN id<3 THEN id ELSE ~id END
And instead of case, use IF:
IF(id<3, id, ~id)
That's because you're ordering by descending ids, so the order is 5-4-3-0-0. You can try:
SELECT * FROM categories ORDER BY CASE WHEN id<3 THEN 9999 ELSE id END DESC
But that is not a perfect solution