performing sql select against a full name using wildcards - sql

I have a stored procedure that I am passing in a general string variable called #SearchText as a varchar. This variable contains names, either part of a name, or a full name. I need to do a select on a table based on this variable, using wildcards. The inbound variable could be anything like (for the name 'john smith'):
'j', 'joh', 'john', 'sm', 'smith', 'john s', john smith'... you get the point.
So, the blunt approach I took is
select x from TableA
where FirstName like '%' + #SearchText + '%'
OR LastName like '%' + #SearchText + '%'
Obviously when a space is encountered it screws up the result set. Can someone please help me understand how to tweak this so it can match on any "amount" of the full name?
If this has already been answered, I couldn't find it... a hotlink to an existing solution would be just as appreciated here.

I might suggest something like this:
where FirstName + ' ' + Lastname like '%' + replace(#Searchtest, ' ', '%') + '%' or
LastName + ' ' + Firstname like '%' + replace(#Searchtest, ' ', '%') + '%'
However, if you are trying to do such full text searches, you might consider using a full text index. That generally provides the right level of functionality for these types of queries.

You can do this as follows:
select x from TableA
where FirstName+' '+LastName like '%' + #SearchText + '%'
Basically, you concatenate the first and last name first and apply the LIKE operator on the concatenation.

Related

How to optimize Impala query to combine LIKE with IN (literally or effectively)?

I need to try and optimize a query in Impala SQL that does partial string matches on about 60 different strings, against two columns in a database of 50+ billion rows. The values in these two columns are encrypted and have to be decrypted with a user defined function (in Java) to do the partial string match. So query would look something like:
SELECT decrypt_function(column_A), decrypt_function(column_B) FROM myTable WHERE ((decrypt_function(column_A) LIKE '%' + partial_string_1 + '%') OR (decrypt_function(column_B) LIKE '%' + partial_string_1 + '%')) OR ((decrypt_function(column_A) LIKE '%' + partial_string_2 + '%') OR (decrypt_function(column_B) LIKE '%' + partial_string_2 + '%')) OR ... [up to partial_string_60]
What I really want to do is decrypt the two column values I'm comparing with, once for each row and then compare that value with all the partial strings, then go onto the next row etc (for 55 billion rows). Is that possible somehow? Can there be a subquery that assigns the decrypted column value to a variable before using that to do the string comparison to each of the 60 strings? Then go onto the next row...
Or is some other optimization possible? E.g. using 'IN', so ... WHERE (decrypt_function(column_A) IN ('%' + partial_string_1 + '%', '%' + partial_string_2 + '%', ... , '%' + partial_string_60 + '%')) OR (decrypt_function(column_B) IN ('%' + partial_string_1 + '%', '%' + partial_string_2 + '%', ... , '%' + partial_string_60 + '%'))
Thanks
Use subquery and also regexp_like can have many patterns concatenated with OR (|), so you can check all alternatives in single regexp, though you may need to split into several function calls if the pattern string is too long:
select colA, ColB
from
(--decrypt in the subquery
SELECT decrypt_function(column_A) as colA, decrypt_function(column_B) as ColB
FROM myTable
) as s
where
--put most frequent substrings first in the regexp
regexp_like(ColA,'partial_string_1|partial_string_2|partial_string_3') --add more
OR
regexp_like(ColB,'partial_string_1|partial_string_2|partial_string_3')
In Hive use this syntax:
where ColA rlike 'partial_string_1|partial_string_2|partial_string_3'
OR ColB rlike 'partial_string_1|partial_string_2|partial_string_3'

Stored procedure with 2 Like parameters

I am looking to use a stored procedure to filter my datagridview by either the user entering the part name into txtPartName or MRPID into txtMRPID. However, this is not filtering as expected and just shows all results from the parts table regardless.
I have a feeling this is due to the way I have implemented the AND or perhaps that I can't perform 2 LIKE statements in one procedure perhaps? Anyway can someone point me in the right direction as how to properly perform this procedure.
CREATE PROCEDURE Parts_ViewAllOrSearch
#PartNameSearch nvarchar(255),
#MRPIDSearch nvarchar(255)
AS
BEGIN
SELECT *
FROM Parts
WHERE #PartNameSearch = ''
OR PartName LIKE '%' + #PartNameSearch + '%'
AND #MRPIDSearch = ''
OR MRP_ID LIKE '%' + #MRPIDSearch + '%'
END
Basically you need parentheses around the OR condition:
SELECT *
FROM Parts
WHERE
(#PartNameSearch = '' OR PartName LIKE '%' + #PartNameSearch + '%')
AND (#MRPIDSearch = '' OR MRP_ID LIKE '%' + #MRPIDSearch + '%')
Why you need that is because AND has higher logical prescedence than OR. So without the parentheses, the WHERE clause is equivalent to:
WHERE
#PartNameSearch = ''
OR (PartName LIKE '%' + #PartNameSearch + '%' AND #MRPIDSearch = '')
OR MRP_ID LIKE '%' + #MRPIDSearch + '%'
... which obviously is not what you want.
Finally, please note that, as it stands, your code just does not seem to really these OR expressions. If a parameter is the empty string, then, once surrounded with wildcards it will match on all possible values (except null values). You would just write this as:
WHERE
PartName LIKE '%' + #PartNameSearch + '%'
AND MRP_ID LIKE '%' + #MRPIDSearch + '%'

How to find multiple words in a string in SQL

I want to be able to take a users search input and find records that match in SQL.
I'm currently using Name like '%' + #SearchText + '%' ) which works fine if they enter in the text the correct way.
Example
If they search for "Jaws Revenge" or "Jaws 2 the revenge" or "revenge jaws" they won't get any results. I want it to return 1 result, id #2 from the table below.
Movies Table
---------------------
ID Name
1 Jaws
2 Jaws 2: The revenge
3 Jaws 3-D
4 Rocky 5000
I've read about full text search but I don't know if that's worth it, the only option, or if there is a more simple solution.
You can replace spaces with %:
Name like '%' + replace(#SearchText, ' ', '%') + '%'
You can use like '%' + replace(#SearchText, ' ', '%') + '%' in expration

Quotes in variable

The variable #it_codigo is used to get a ntext value from other table in a procedure and is used for a select like:
SELECT * FROM anaProdutos WHERE cod_produto LIKE #it_codigo
But this doesn't work, missing quotes. I tried
''+#it_codigo+''
and
QUOTENAMES(#it_codigo, '')
But that didn't solve the problem.
If you're using LIKE you'd want something as per below;
LIKE '%' + #it_codigo + '%'
You need the percentage signs for the LIKE to work.
Try
WHERE cod_produto LIKE '%' + #it_codigo + '%'
Check this link for more information on LIKE keyword.

How to do an IN on a subquery with a CSV?

I have the following varchar value '1,2,4,5, ...' in a table column.
Basically, they're just codes in CSV format. I know it's a bad design, but that's what I have to deal with unfortunately.
Now I want to create a subquery to find descriptions that correspond to all codes.
How do I do that?
I've tried a subquery like
SELECT description FROM table WHERE table.CODE IN tablewithcsv.csvcolumn
But to no avail.
Normal IN's expect values like ('1', '2', '3'), but I suspect my value gets passed as '1,2,3'. Do I have to do some replacing here?
To search in a string, you can use:
SELECT description FROM `table`
INNER JOIN `tablewithcsv` ON `tablewithcsv`.csvcolumn LIKE '%' + `table`.CODE + '%'
This will work if the integers are only on character long, but will return false positives on more than one char. If you have more than one char, you can change it as such:
SELECT description FROM `table`
INNER JOIN `tablewithcsv` ON `tablewithcsv`.csvcolumn = `table`.CODE
OR `tablewithcsv`.csvcolumn LIKE `table`.CODE + ',%'
OR `tablewithcsv`.csvcolumn LIKE '%,' + `table`.CODE
OR `tablewithcsv`.csvcolumn LIKE '%,' + `table`.CODE + ',%'
This could also be done more elegantly using regular expressions