SQL: finding similar rows to other same table in special column - sql

I am using SQLITE for running this query:
SELECT * FROM phrases1, phrases2 WHERE phrases1.word LIKE ('%' +phrases2.word+ '%')
but not works.
two tables phrases1, phrases2 are same and have column name word and I want to filter the first table by rows that word column is similar to the word column of second table . while this works:
SELECT * FROM phrases1, phrases2 WHERE phrases1.word LIKE phrases2.word
but I want to use wildcards.

The SQLite operator for string concatenation is || not +:
SELECT * FROM phrases1, phrases2
WHERE phrases1.word LIKE '%' || phrases2.word || '%'
Also I don't know what the effect of having parentheses around your LIKE expression would be, but you don't need them there. But you should really write your query using explicit joins, better yet use aliases too:
SELECT *
FROM phrases1 p1
INNER JOIN phrases2 p2
ON p1.word LIKE '%' || p2.word || '%'

Related

Can you explain the following SQL (postgres) code?

I asked SO for a query to find all rows in a table with a 'code' entry that is a substring of the search string, with the added condition that it appears at the end of the search string.
So a query for '12345' should return '2345', '345', '45', and '5'.
I was given this answer, which works. I have read through the documentation but still don't understand the query. Can someone please explain
SELECT * from yourtable
where '12345' like '%' || Code
Normally a LIKE is used in the opposite way.
For example:
SELECT * FROM SomeTable
WHERE SomeColumn LIKE '%xxx%'
So you check if the column matches against a fixed string with a pattern.
But the clever thing about that answer was it did the opposite.
It checks a fixed string again a pattern that's created from a column.
SELECT * FROM SomeTable
WHERE 'bar456' LIKE '%' || SomeColumn;
In this example, if "SomeColumn" contains the value "56"?
Then '%' || SomeColumn forms the string '%56'
So 'bar456' is like '%56', since it ends with '56'
And 'bar456' is also like '%ar456'
There are two relevant documentation links you need:
PostgreSQL Pattern Matching: '12345' like '%'
PostgreSQL CONCATENATE(||) Operator: <match> || Code
The SQL means:
Fetch all columns from the table
IF column "code" is equal to <match> + <value of "code" column>

substring match on both tables of a join

How can I perform joins on a substring match to another substring. I seem to only be able to ilike search on one or the other, not substring search both.
Given tables:
DIALOG
string
-------------------
Hi, my name is dan
STRUCTURES
structure
----------
his name is / my name is
hello, my / you are
how are you?
EXPECTED OUTPUT:
string | structure
-------------------------------
Hi, my name is dan | his name is / my name is
Attempts:
Two ilike fuzzy matches:
select string, structure from dialog left join structures on ('%' || string || '%' ilike '%' || structure || '%');
Two fuzzy ilike matches with OR:
select string, structure from dialog left join structures on (string ilike '%' || structure || '%') or (structure ilike '%' || string || '%');
Both output:
string | structure
-------------------------------
Hi, my name is dan |
If the structures actually matches, you could use regular expressions:
select string, structure
from dialog d left join
structures s
on string ~ replace(string, ' / ', '|');
Of course, this doesn't work on the sample data, because the strings don't actually match.
This also suggests that your structure should actually be a regular expression.
Perform a cartesian product first, limited with a WHERE clause, to see what kind of results you can expect.
select string, structure from dialog CROSS join structures WHERE string ilike '%' || structure || '%' AND structure ilike '%' || string || '%'
I think your left join attempt does not match anything because there's wildcards on the left side of the ILIKE statement. These are, afaik, taken literally. Also, use 'AND' for the join: you want the couples where both of the predicates are true. The cross join fits OK here, as you define your where clause pretty tightly.
The left join would only be used where you want to absolutely get your 'dialog', with optionally 'structure' connected to it. In this case, do the 'full join', so you can see exactly what kind of matches are made. Later on, you can decide to further filter everything out and put the where clause predicates in suitable join clause.

How to use multiple LIKE statements in a query with IN clause and a subquery? [duplicate]

This question already has answers here:
Using LIKE in an Oracle IN clause
(11 answers)
Closed 6 years ago.
If I want to select some objects from dba_source which uses some function.
I can write it like
Select * from dba_source where text like '%some_name%';
If I want to do the same thing for multiple names. How do i do it?
I'm aware of the usage of LIKE and OR, but the Names am getting are again from another table. So, Is there a way to do something like:
SELECT * FROM DBA_SOURCE WHERE TEXT LIKE IN(SELECT PROCESS_NAME FROM PROCESSES);
But I also want to add Wild card characters like % at the ends.
Is it possible. or can you suggest any other way?
I also tried
WITH pnames AS (SELECT PROCESS_NAME FROM PROCESSES)
SELECT * FROM DBA_SOURCE dbas WHERE INSTR(dbas.text,pnames.process_name,1,1)>0;
It didn't work.
Joining with % || % is a good idea. But, It takes more time to run. Is there any better way to deal with this
SELECT *
FROM DBA_SOURCE d
JOIN PROCESSES p ON d.TEXT like '%' || p.PROCESS_NAME || '%'
|| is ANSI SQL concatenation. I assume at least newer Oracle versions support it. Otherwise you may need to try CONCAT() function instead.
Use a join between the tables and let the condition by the like
SELECT D.*
FROM DBA_SOURCE D
JOIN PROCESSES P
ON D.TEXT LIKE PROCESS_NAME || '%'

"NOT IN" subquery with a leading wildcard

I have two tables:
Table tablefoo contains a column fulldata.
Table tablebar contains a column partialdata.
I want find a list of tablefoo.fulldata that do NOT have partial matches in tablebar.partialdata.
The following provides a list of tablefoo.fulldata with partial matches in tablebar, but I want the negative of this.
select fulldata from tablefoo
where fulldata like any (select '%' || partialdata from tablebar);
This lists every record in partialdata:
select fulldata from tablefoow
where partialdata not in (select '%' || partialdata from tablebar);
Any idea how to get only the results tablefoo.fulldata that do not contain matches to a leading wildcarded tablebar.partialdata?
I found this link: PostgreSQL 'NOT IN' and subquery which seems like it's headed down the right path, but I'm not getting it to work with the wildcard.
Sure, I could write a script to pull this out of psql and do the comparisons, but it would be much nicer to handle this all as part of the query.
SELECT fulldata
FROM tablefoo f
WHERE NOT EXISTS (
SELECT 1
FROM tablebar b
WHERE f.fulldata LIKE ('%' || b.partialdata)
);

MySQL: JOIN two tables on LIKE

I have a table with a column containing text, and I want to select all of the tables where the text from one of the rows in a second table appears in that row. Here is a pseudo-query:
SELECT title FROM recipes AS r
JOIN ingredients AS i
ON r.ingredients LIKE '%' + i.name + '%';
The above query does not work, however. How do I do this correctly?
SELECT title
FROM recipes r JOIN ingredients i ON r.ingredients LIKE concat('%', i.name, '%')
MySQL is weird, and makes you use the concat operator to concatenate strings together. Most others use ||
You can't concatenate strings with the + operator (it's for arithmetic only). Use concat('%',i.name,'%') instead.