I have a MySQL database table that contains column run that is an integer and another column filename that is a varchar with typical values like RUN0001.FTS or 3DS0231.FTS or 3RUN0010.FTS
I need to check the values in the run and filename columns. The prescription is I extract the last integer (without leading zeroes) before the dot character (.) in the filename column, and compare it to the value of the run column. How do I write a select statement to do this comparison to return the rows that will not have the matching integers?
For example, a regular expression I am trying to build would extract 1 from RUN0001.FTS, or 231 from 3DS0231.FTS, or 10 from 3RUN0010.FTS and then compare it to the value in the run column, and return the primary key if the two don't match.
In Python I would manipulate the variable filename = '3RUN0010.FTS' like so:
import re
filename = '3RUN0010.FTS'
fileRunNumber = re.findall('\d+', filename)
runNumber = int(fileRunNumber[-1])
print "The integer I want is", runNumber
How do I do this in as a MySQL statement?
Thanks,
Aina.
You can try the following query:
SELECT CAST(SUBSTRING(col, INSTR(col, '.') - 4, 4) AS UNSIGNED) AS theNumber
FROM yourTable
Data:
CREATE TABLE yourTable (col varchar(55));
INSERT INTO yourTable (col)
VALUES
('RUN0001.FTS'),
('3DS0231.FTS'),
('3RUN0010.FTS');
Output:
Demo here:
Rextester
Related
I have a table as:
id: Int,
URL: string,
//other fields
The URL field contains values like ["nytimes.com/live/", "prisma.io/docs/reference/api-reference/", "stackoverflow.com/questions",...]
How do I query to only get the domains of URLs ["nytimes.com", "prisma.io", "stackoverflow.com"...]
Right now I am doing it by fetching all the records and capturing the domain in server. I was wondering if there is a way to do this in SQL directly?
SELECT SUBSTRING_INDEX(URL, '/', 1) FROM table ;
In SQL Server,
CHARINDEX returns the position of a given character.
SUBSTRING returns the substring from the start of the string until the given index
Hence, combining CHARINDEX and SUBSTRING function, we can get the domain name.
Eg, if the domain name is google.com, the following query will return 'google'
SELECT SUBSTRING(URL, 1, CHARINDEX('.',URL)) FROM table_name
The solution for mysql database given by #ricardo-francois works just as intended.
CREATE TABLE domains (id int auto_increment primary key, url varchar(100) not null);
INSERT INTO domains(url) values('nytimes.com/live/'),('google.com/crawl');
SELECT SUBSTRING_INDEX(URL, "/",1) FROM table_name;
The last parameter 1 in the SUBSTRING function indicates the number of occurrences of the delimiter. Here, it will return all the texts until the first delimiter (which is "/")
Output :
nytimes.com
google.com
I'm trying to quickly insert large number of rows into the following table:
CREATE TABLE word
(word_id int(10) PRIMARY KEY AUTO_INCREMENT ,
word_txt VARCHAR(40) NOT NULL UNIQUE)
using executemany() :
query = "INSERT IGNORE INTO word (word_txt) VALUES (%s)"
try:
self.cursor.executemany(query,word_list)
except ...
word_list is a list of single string tuples.
e.g: word_list = [('cases',), ('regard',), ('disregard',), ...]
Interface Error returns at execution: "No result set to fetch from".
using an alternative:
query = f"INSERT IGNORE INTO word (word_txt) VALUES {words}"
try:
self.cursor.execute(query)
except
according to MySQL the syntax is invalid after execution.
same as before words is a list of of single string tuples.
the value of (string) variable "query" at the moment of debugging:
query = INSERT IGNORE INTO word (word_txt) VALUES [('tire',), ('object',), ('really',), ...,('these',), ('regarded',)]
Would appreciate any help.
I have MySQL installed locally, running SELECT VERSION() returns this value: 5.6.43-84.3
When I run a query it is returning multiple rows when it should only return 1 row. Let me set it up, it's easier to explain that way.
Create a test table:
CREATE TABLE test_table
(
test_val VARCHAR(255)
)
;
Load 3 values into the table:
INSERT INTO test_table (test_val)
VALUES
('9671986020630615'),
('9671986020630616'),
('9671986020630617')
;
Run this query (This query returns 1 row which is expected):
SELECT *
FROM test_table
WHERE test_val = '9671986020630615'
;
Run this query (This query returns 3 rows, which it shouldn't):
SELECT *
FROM test_table
WHERE test_val = 9671986020630615
;
Here's what I have observed about this situation:
The first query surrounds the value in the WHERE clause with single quotes.
The second query does not surround the value in the WHERE clause with single tics.
The column in the test table is defined as VARCHAR(255)
It makes sense that the first query returns just one row because it's comparing a string from the WHERE clause to a string value in the test table (VARCHAR(255))
Something is happening when MySQL compares the numerical value in the WHERE clause of the second query to the string value in the test table (VARCHAR(255)) which is causing MySQL to return 3 rows instead of just 1.
It makes sense that the first query returns the correct result because it is comparing a string to a string.
It also makes a degree of sense that the second query is returning a bad dataset (3 rows as opposed to the 1 row it should return).
But my question is why is MySQL doing this? Why when it compares a number to 3 different VARCHAR(255) values does it return all 3 rows when the true value of the numerical value in the WHERE clause only matches 1 row?
So, in essence for the first query MySQL is saying:
'9671986020630615' = '9671986020630615',
'9671986020630615' <> '9671986020630616',
'9671986020630615' <> '9671986020630617'
but for the second query it is saying:
9671986020630615 = '9671986020630615',
9671986020630615 = '9671986020630616',
9671986020630615 = '9671986020630617'
Any help will be much appreciated.
MySQL handles all numbers internally the same way Javascript does, with IEEE double-precision floating point representation.
When you omit the quotation marks from your long numeric strings, that is you write 9671986020630615 in place of '9671986020630615 ', MySQL uses the number. Then, when it runs the WHERE part of your query, it silently coerces each column value to a double precision number.
But due to the machine epsilon -- the limit of precision -- of double precision, 9671986020630615, 9671986020630616, and 9671986020630617 all have the same value. So the WHERE finds all three.
CAST(9671986020630615 AS DOUBLE) CAST(9671986020630616 AS DOUBLE) CAST(9671986020630617 AS DOUBLE)
9.671986020630616e15 9.671986020630616e15 9.671986020630616e15 |
See how all three integers have the same representation as DOUBLE?
I'm trying to update my table column values into a string. My query goes like this
UPDATE tbl_testing
SET result= 'Hey'
WHERE (SELECT (colOne) + '-' + (colTwo) + '-' + (colThree)) = 'r-r-r'
which the columns 'colOne, colTwo and colThree' already contains 'r' but slqyog shows "Truncated incorrect DOUBLE value: 'r-r-r'"
and all of the other result column data became = 'Hey'. What should I do?
You have to decide it is either MySQL or MSSQL.
In MySQL the string concatenation is not + sign, but simply you enumerate the columns separated by comma and the statement is SELECT CONCAT("Field1", "Field2" etc) AS ConcatenatedString); - CONCAT() function.
Try reevaluate your DB engine and adapt the query.
In MSSQL the string concatenation is indeed + sign. Your query works ok in MSSQL and updates the result column with the value you have set.
DDL
CREATE TABLE [dbo].[tbl_testing](
[id] [int] NULL,
[result] [nvarchar](4000) NULL,
[colOne] [nvarchar](4000) NULL,
[colTwo] [nvarchar](4000) NULL,
[colThree] [nvarchar](4000) NULL
) ON [PRIMARY]
GO
INSERT INTO tbl_testing (id, colOne, colTwo, colThree)
VALUES (1, 'r', 'r', 'r')
Update statement
UPDATE tbl_testing
SET result='Hey. I am a concatenated string'
WHERE (SELECT (colOne)+'-'+(colTwo)+'-'+(colThree))='r-r-r'
Output
id result colOne colTwo colThree
1 Hey. I am a concatenated string r r r
Changing comment to answer:
You should avoid doing that statements in that way. By doing that, database use no indexes and also you are giving more computation tasks to database server (server needs to concatenate all values and after concatenations will compare with given string).
Better way is to replace yours where statement with something like:
`WHERE colOne = 'r' AND colTwo = 'r' AND ...`
that will work faster without additional computation need (to concatenate strings).
This solution works much much faster, and looks much much better.
I have a table and I have added a new column to it. I need to populate this new column and also set the default value for it.
The value of the new col is obtained by concatenating two strings based on the values of other columns:
the first string is the sum COL_1 + 10000
the second string is a obtained by stripping everything but the alphanumerics in COL_2
Update TABLE set NEW_COL = CONCAT ((SUM (10000 + COL_1)), (preg_replace('/[\s\W]+/','',COL_2)))
This will be the default value for the column
The reason your update is failing is that preg_replace() is not a valid MySQL function. That's a PHP function. Here's a relevant question that addresses that functionality in MySQL:
How to do a regular expression replace in MySQL?