Getting empty result if there is 'null' value in CONCAT - mysql

I expected to get full name without middle initial if there is no middle name, but if column "M_NAME" is Null, the select statement returns empty. How can i solve this?
SELECT CONCAT(`Employee`.`F_NAME`, ' ', LEFT(`Employee`.`M_NAME`, 1), '. ', `Employee`.`L_NAME`) FROM `ccms`.`Employee` WHERE HR_ID = '223';

CONCAT returns NULL if any argument is null. You can solve this by making sure that no null argument is null by wrapping any nullable column in either IFNULL or COALESCE (the latter can take more than two arguments).
SELECT
CONCAT(
IFNULL(F_NAME, ''),
' ',
IFNULL(CONCAT(LEFT(M_NAME, 1), '. '), ''),
IFNULL(L_NAME, '')
)
FROM
ccms.Employee
WHERE
HR_ID = '223';
What this does is replace NULL column values with an empty string, which is probably your intent. Note that I updated the selection of M_NAME so that the period is only added if the value is not null by using this very behavior.
EDIT: You can use backticks and qualify column names if you want, but it's not necessary for this exact query.

Use COALESCE()
Returns the first non-NULL value in the list, or NULL if there are no non-NULL values.
SELECT CONCAT(`Employee`.`F_NAME`, ' ', COALESCE(LEFT(`Employee`.`M_NAME`, 1), ''), '. ', `Employee`.`L_NAME`) FROM `ccms`.`Employee` WHERE HR_ID = '223';

Use IFNULL().
Any place you have a possibly NULL field, wrap it with IFNULL(whatever, '') and then you'll get an empty string instead of a result-killing NULL.

another simple solution is use CONCAT_WS. It will work defenitely.
SELECT
CONCAT_WS(''
F_NAME,
'',
LEFT(M_NAME, 1),
L_NAME) FROM
ccms.Employee WHERE HR_ID = '223';

Related

Mysql combine columns if not null

I know that I can combine multiple columns in mysql by doing:
SELECT CONCAT(zipcode, ' - ', city, ', ', state) FROM Table;
However, if one of the fields is NULL then the entire value will be NULL. So to prevent this from happening I am doing:
SELECT CONCAT(zipcode, ' - ', COALESE(city,''), ', ', COALESCE(state,'')) FROM Table;
However, there still can be situation where the result will look something like this:
zipcode-, ,
Is there a way in MySQL to only have to comma and the hyphen if the next columns are not NULL?
There is actually a native function that will do this called Concat with Separator (concat_ws)!
Specifically, it seems that what you would need is:
SELECT CONCAT_WS(' - ',zipcode, NULLIF(CONCAT_WS(', ',city,state),'')) FROM TABLE;
This should account for all of the null cases you allude to.
However, it is important to note that a blank string ('') is different than a NULL. If you want to address this in the state/city logic you would add a second NULLIF check inside the second CONCAT_ws for the case where a city or a state would be blank strings. This will depend on the database's regard for the blank field and whether you are entering true NULLS into your database or checking the integrity of the blank data before you use it. Something like the following might be slightly more robust:
SELECT CONCAT_WS(' - ', zipcode, NULLIF(CONCAT_WS(', ', NULLIF(city, ''), NULLIF(state, '')), '')) FROM TABLE;
For more, check out the native documentation on concat_ws() here:
https://dev.mysql.com/doc/refman/8.0/en/string-functions.html#function_concat-ws
I think you need something like this
Set #zipcode := '12345';
Set #city := NULL;
Set #state := NULL;
SELECT CONCAT(#zipcode, ' - ', COALESCE(#city,''), ', ', COALESCE(#state,''));
Result: 12345 - ,
SELECT CONCAT(#zipcode, IF(#city is NULL,'', CONCAT(' - ', #city)), IF(#state is NULL,'', CONCAT(', ',#state)))
Result 12345
You need to make the output of the separators conditional on the following values being non-NULL. For example:
SELECT CONCAT(zipcode,
CASE WHEN city IS NOT NULL OR state IS NOT NULL THEN ' - '
ELSE ''
END,
COALESCE(city, ''),
CASE WHEN city IS NOT NULL AND state IS NOT NULL THEN ', '
ELSE ''
END,
COALESCE(state, '')
) AS address
FROM `Table``
Output (for my demo)
address
12345 - San Francisco, CA
67890 - Los Angeles
34567 - AL
87654
Demo on dbfiddle

Updating blank cells to NULL causes ALL cells to be NULL

I have a query that I'm trying to use to update only cells with empty strings to NULL. But instead, when I run this command ALL of the cells end up being NULL:
UPDATE table_name
SET InvoiceId=NULL,
LinkedAccountId=NULL,
RecordId=NULL,
ProductName=NULL,
RateId=NULL,
SubscriptionId=NULL,
PricingPlanId=NULL,
UsageType=NULL,
Operation=NULL,
AvailabilityZone=NULL,
ReservedInstance=NULL,
UsageStartDate=NULL,
UsageEndDate=NULL,
UsageQuantity=NULL,
BlendedRate=NULL,
UnBlendedRate=NULL,
ResourceId=NULL,
Engagement=NULL,
Name=NULL,
Owner=NULL,
Parent=NULL
WHERE InvoiceId=''
OR LinkedAccountId=''
OR RecordId=''
OR ProductName=''
OR RateId=''
OR SubscriptionId=''
OR PricingPlanId=''
OR UsageType=''
OR UsageEndDate=''
OR Operation=''
OR AvailabilityZone=''
OR ReservedInstance=''
OR UsageStartDate=''
OR UsageEndDate=''
OR UsageQuantity=''
OR BlendedRate=''
OR UnBlendedRate=''
OR ResourceId=''
OR Engagement=''
OR Name=''
OR Owner=''
OR Parent='';
What am I doing wrong?
You are setting ALL fields to NULL where any field = ''
You might need to write as many queries as fields you want to update.
I might be wrong, but I don't think this is possible to do in a single query
UPDATE table_name
SET InvoiceId = NULL
WHERE InvoiceId = ''
And this for every fields
The way to interpret your SQL query is kind of like this:
UPDATE table_name
SET
(all these fields to null)
WHERE
(if ANY Of these conditions is true)
I agree with Cid that it might be the safest to do 1 field per query at a time, but this is how you could write this in a single query:
UPDATE table_name SET
field1 = IF(field1='',NULL,field1),
field2 = IF(field2='',NULL,field2),
/* etc */
I think you're assuming that the terms in your WHERE clause have an implicit correlation with the assignments in your SET clause, so only some columns will be set, depending on which ones satisfy individual terms in the WHERE clause. This is not how SQL works.
What really happens is that the whole condition of the WHERE clause is evaluated to select which rows are affected. Then all the SET assignments are applied, so all columns will be changed on the rows that satisfy the whole WHERE clause condition.
To do what you want in one pass, you could do it this way:
UPDATE table_name
SET InvoiceId=NULLIF(InvoiceId, ''),
LinkedAccountId=NULLIF(LinkedAccountId, ''),
RecordId=NULLIF(RecordId, ''),
ProductName=NULLIF(ProductName, ''),
RateId=NULLIF(RateId, ''),
SubscriptionId=NULLIF(SubscriptionId, ''),
PricingPlanId=NULLIF(PricingPlanId, ''),
UsageType=NULLIF(UsageTYpe, ''),
Operation=NULLIF(Operation, ''),
AvailabilityZone=NULLIF(AvailabilityZone, ''),
ReservedInstance=NULLIF(ReservedInstance, ''),
UsageStartDate=NULLIF(UsageStartDate, ''),
UsageEndDate=NULLIF(UsageEndDate, ''),
UsageQuantity=NULLIF(UsageQuantity, ''),
BlendedRate=NULLIF(BlendedRate, ''),
UnBlendedRate=NULLIF(UnBlendedRate, ''),
ResourceId=NULLIF(ResourceId, ''),
Engagement=NULLIF(Engagement, ''),
Name=NULLIF(Name, ''),
Owner=NULLIF(Owner, ''),
Parent=NULLIF(Parent, '')
The NULLIF() function returns NULL if its two arguments are equal, otherwise it returns the first argument. So in the case that each column is not '' then it is a no-op, setting the column to its own original value.

Why CONCAT does not insert text for the first time into mySQL table?

I am using UPDATE to insert simple text into a table where the field is MEDIUMTEXT (nullable field).
It is strange that it does not work when the field is null initially. If I manually enter at least a one character/space, then it's working.
I want to append the new text into existing text in the field.
UPDATE pen SET
PEN_STATUS = #PenStat,
PEN_STATUS_CHANGE_REASON = CONCAT(PEN_STATUS_CHANGE_REASON,'\n',ChangeDate,':',EmployeeID,':',ChangeReason)
WHERE PEN_ID = PenID;
Why is this?
CONCAT does not handle NULL values. As explained in the MySQL manual:
CONCAT() returns NULL if any argument is NULL.
You want to use COALESCE to handle that use case, like :
UPDATE pen SET
PEN_STATUS = #PenStat,
PEN_STATUS_CHANGE_REASON = CONCAT(
COALESCE(PEN_STATUS_CHANGE_REASON, ''),
'\n',
ChangeDate,
':',
EmployeeID,
':',
ChangeReason
)
WHERE PEN_ID = PenID;
Presumably, because something is NULL. Try using CONCAT_WS() instead:
UPDATE pen
SET PEN_STATUS = #PenStat,
PEN_STATUS_CHANGE_REASON = CONCAT_WS('\n',
PEN_STATUS_CHANGE_REASON,
CONCAT_WS(':', ChangeDate, EmployeeID, ChangeReason
)
)
WHERE PEN_ID = PenID;
CONCAT_WS() ignores NULL arguments. Plus, the separator only needs to be listed once.

MySQL: Extract regexp value from query

I would need to get value from given regexp.
For example:
> :"postalCode";s:4:"3150";
Is there any way I can extract 3150, from this part of column value. Column value stored serialized objects, so postalCode variable can be null type, that way I should check if positive integer follows ;s:POSITIVE_INT:"postalCodeValue
Use SUBSTRING_INDEX:
SELECT
SUBSTRING(SUBSTRING_INDEX(col, '"', -2), 1,
INSTR(SUBSTRING_INDEX(col, '"', -2), '"') - 1) AS num
FROM yourTable;
This query will extract the last quoted number in your string.
Demo
avoiding regexp you could use some string function eg:
SELECT LENGTH(':"postalCode";s:4:"3150"') - LOCATE(':', REVERSE(':"postalCode";s:4:"3150"'))+1
from dual ;
or
SELECT LENGTH(col_name) - LOCATE(':', REVERSE(col_name))+1
from my_table ;
It also work with 2 times SUBSTRING_INDEX
SELECT
SUBSTRING_INDEX (SUBSTRING_INDEX( ':"postalCode";s:4:"3150";', '"',-2) , '"', 1);

Conditional CONCAT with potentially NULL or empty values

In the below piece of code, I am creating an Address field by concatenating various parts of an address.
However, if for instance address2 was empty, the trailing , will still be concatenated into Address.
This means if all fields were empty, I end up with a result of ,,,,.
If address1 is "House Number" and everything else is empty, I end up with House Number,,,,.
CONCAT( COALESCE(address1,'') , ', ' ,
COALESCE(address2,'') , ', ' ,
COALESCE(address3,'') , ', ' ,
COALESCE(city,'') , ', ' ,
COALESCE(zip, '')
) AS Address,
Is there some way of conditionally placing the commas between address parts only if the content of an address part is not empty.
Such as something along the lines of (pseudo-code) IF(address1) is NULL use '' ELSE use ','
Thank you.
CONCAT_WS(', ',
IF(LENGTH(`address1`),`address1`,NULL),
IF(LENGTH(`address2`),`address2`,NULL),
IF(LENGTH(`address3`),`address3`,NULL),
IF(LENGTH(`city`),`city`,NULL),
IF(LENGTH(`zip`),`zip`,NULL)
)
Using CONCAT_WS as Mat says is a very good idea, but I thought I'd do it a different way, with messy IF() statements:
CONCAT( COALESCE(address1,''), IF(LENGTH(address1), ', ', ''),
COALESCE(address2,''), IF(LENGTH(address2), ', ', ''),
COALESCE(address3,''), IF(LENGTH(address3), ', ', ''),
COALESCE(city,''), IF(LENGTH(city), ', ', ''),
COALESCE(zip,''), IF(LENGTH(address1), ', ', ''),
) AS Address,
The IF()s check if the field has a length and if so returns a comma. Otherwise, it returns an empty string.
try with MAKE_SET
SELECT MAKE_SET(11111,`address1`,`address2`,`address3`,`city`,`zip`) AS Address
It will returns a string with all NOT NULL value separated by ,
CONCAT_WS(', ',
NULLIF(`address1`,''),
NULLIF(`address2`,''),
NULLIF(`address3`,''),
NULLIF(`city`,''),
NULLIF(`zip`,'')
)
CONCAT_WS combines non-NULL strings.
NULLIF writes NULL if left and right side are equals. In this case if values are equals an empty sting ''.