I am trying to group rows by a field that either has the pattern [:alpha:][:digit:].* or [:alpha:][:alpha:][:digit:].* by the substring up to but excluding the digit. i.e. the returned substring will either have one letter, or two.
I am thinking something along the lines of:
SELECT
LEFT(postcode,IF(ISDIGIT(postcode,2),1,2)) AS area,
COUNT(*) AS num
FROM addresses
GROUP BY
LEFT(postcode,IF(ISDIGIT(postcode,2),1,2))
Except of course there is no ISDIGIT() function.
I was also thinking of something similar to LEFT(postcode,POSITION_REGEX("\d" IN postcode)) but obviously that doesn't exist either :-/
Database server is running MySQL 4.1.24
Upgrading to 5.0 is possible but would require downtime and hasn't been done yet as it hasn't been necessary so far.
SELECT
LEFT(postcode, IF(postcode REGEXP '^.[[:digit:]]', 1, 2)) AS area,
COUNT(*) AS num
FROM addresses
GROUP BY area
Related
When I run the following query, I am returned two entries with duplicate results. Why are duplicate results returned when I’m using distinct here? The primary keys are the house number, street name, and unit number.
SELECT distinct
house_num,
Street_name,
Unit_Designator,
Unit_Num
FROM voterinfo.voter_info
WHERE house_num = 420
AND street_name = "PARK"
AND Unit_Num = ''
AND Unit_Designator = '';
select distinct is a statement that ensures that the result set has no duplicate rows. That is, it filters out rows where every column is the same (and NULL values are considered equal).
It does not look at a subset of columns.
Sometimes, people use select distinct and don't realize that it applies to all columns. It is rather amusing when the first column is in parentheses -- as if parentheses make a difference (they don't).
Then, you might also have situations where values look the same but are not.
Consider this simple example where values differ by only a space as the end of string:
select distinct x
from (select 'a' as x union all
select 'a '
) y;
Here is a db<>fiddle with this example.
This returns two rows, not 1.
Without sample data it is hard to say which of these situations you are referring to. But the rows that you think are "identical" really are not.
For the fields with datatype as Char or similar ( Street_name,Unit_Designator) it is possible that there are spaces that aren't visible in the query editor that are to be removed by applying appropriate trimming logic.Please refer below link,
MySQL select fields containing leading or trailing whitespace
I have a group of records that look like these following notional results. There are multiple occurrences where the number in the count column is repeated. 'count' comes from char_length(text_column). I want to grab the first record in each such grouping. How do I do this?
I've looked at the char_length() documentation and searched for examples where this has been done, but can't find anything.
select distinct(char_length(text_column)), text_column from table
.... is as close -- which is not obviously close -- as I've been able to get to the result.
=======+============================
count + text_column
=======+============================
2139 + some text entry
-------+----------------------------
3000 + another sentence here
-------+----------------------------
3000 + more text in this sentence
-------+----------------------------
3000 + still more text here
-------+----------------------------
Thank you,
BW
There is no such thing as "first" unless a column specifies the ordering. You can, however, get a value from an indeterminate row by using group by:
select char_length(text_column), text_column
from table
group by char_length(text_column);
I'm not a big fan of using the MySQL extension to group by where text_column is allowed in the select, but not the group by. However, because it is a long column, it might be more efficient to just let MySQL pick the value rather than using an actual aggregation function (such as min() or max()).
I have a simple query with a few rows and multiple criteria in the where clause but it is only returning one row instead of 13. No joins and the syntax was triple checked and appears to be free of errors.
Query:
select column1, column2, column3
from mydb
where onecolumn in (number1, number2....number13)
Results:
returns one row of data associated with a random number in the where clause
spent a big part of the day trying to figure this one out and am now out of ideas. Please help...
Absent a more detailed test case, and the actual SQL statement that is actually running, this question cannot be answered. Here are some "ideas"...
Our first guess is that the rows you think are going to satisfy the predicates aren't actually satisfying all of the conditions.
Our second guess is that you've got an aggregate expression (COUNT(), MAX(), SUM()) in the SELECT list that's causing an implicit GROUP BY. This is a common "gotcha"... the non-standard MySQL extension to GROUP BY which allows non-aggregates to appear in the SELECT list, which are not also included as expressions in the GROUP BY clause. This same gotcha appears when the GROUP BY clause is omitted entirely, and an aggregate is included in the SELECT list.
But the question doesn't make any mention of an aggregate expression in the SELECT list.
Our third guess is another issue that beginners frequently overlook: the order of precedence of operations, especially AND and OR. For example, consider the expressions:
a AND b OR c
a AND ( b OR c )
( a AND b ) OR c
consider those while we sing-along, Sesame Street style,...: "One of these things is not like the others, one of these things just doesn't belong..."
A fourth guess... if it wasn't for the row being returned having a value of onecolumn as a random number in the IN list... if it was instead the first number in the IN list, we'd be very suspicious that the IN list actually contains a single string value that looks like a list a values, but is actually not.
The two expression in the SELECT list look very similar, but they are very different:
SELECT t.n IN (2,3,5,7) AS n_in_list
, t.n IN ('2,3,5,7') AS n_in_string
FROM ( SELECT 2 AS n
UNION ALL SELECT 3
UNION ALL SELECT 5
) t
The first expression is comparing n to each value in a list of four values.
The second expression is equivalent to t.n IN (2).
This is a frequent trip up when neophytes are dynamically creating SQL text, thinking that they can pass in a string value and that MySQL will see the commas within the string as part of the SQL statement.
(But this doesn't explain how a some the random one in the list.)
Those are all just guesses. Those are some of the most frequent trip ups we see, but we're just guessing. It could be something else entirely. In it's current form, there is no definitive "answer" to the question.
I came across a scenario where i have values in a coloumn like
Buno foo
Buno this
Buno that
Buno bar
This is the values of a single coloumn,Now i want to sort this coloumn excluding the
Buno
word,means sorting should be applied on foo,this,that and bar.Is there a way to do this in MySql?
Select * from tableName order by Column_Name
This query can get you the required results, you dont have to worry about the first word.
database query sorts on the first word, if the first word is same, then its sorts according to the second word.
If I am not mistaken, using ORDER BY will sort the entire value in the column, not just the first word, so you should just be able to use ORDER BY to solve your problem...
If you wanted to remove the first section though, you would need to use SUBSTRING in your SELECT and then ORDER BY your substring...
EDIT: Saw your comment above on not knowing how to use SUBSTRING, here is an example using your data:
SELECT SUBSTRING('Buno Foo', 5) AS NOBuno FROM MyTable ORDER BY NOBuno ASC
You can extract the substring of your column from the 6th character onwards (since you always have Buno at the front, which is 5 characters long). To do this use SUBSTRING:
SELECT ...
FROM ...
ORDER BY SUBSTRING(my_column FROM 6)
Note that SELECT SUBSTRING(my_column FROM 6) will return foo,this,that, etc.
If you wanted to be a bit more general and order using the second word, you can try SUBSTRING_INDEX. (read the docs and you'll work it out).
I am using a MySQL Database to search through a list of categories. My query is:
select * from cat where name REGEXP('(region_Long Island)+(.)*(sport_Outdoor Track)');
where the values "region_Long Island" and "sport_Outdoor Track" are passed in. I need to be able to match these categories, regardless of the order they are in. In the table, it is possible to have various combinations of these two categories. I need to match any records that have both of these categories, regardless of what order they are listed in.
I am not able to change the query itself, only modify what is passed into th REGEXP function.
Thank you
If you can use only a single regexp and you can't change the SQL query, then to match both A and B in any order, you need a regexp that matches AB or BA:
'region_Long Island.*sport_Outdoor Track|sport_Outdoor Track.*region_Long Island'
Re your comment:
What about cases where there are more than two, in any particular order?
If you had patterns A, B, and C any you needed to find all three in any order, you'd need a regexp that matches ABC, ACB, CAB, CBA, BAC, or BCA. This quickly starts to look like you need n! permutations if you have n patterns.
That's why a single regular expression is not a good solution for these cases. You're going to have to use another approach.
I am not able to change the query itself, only modify what is passed into the REGEXP function.
Sorry, that's not going to work.
SELECT *
FROM cat
WHERE name RLIKE 'region_Long Island'
AND name RLIKE 'sport_Outdoor Track'