Java 8 will replace String with String2, which will treat empty string and null the same.
By by characterZer0 (138196), on Monday April 20, @08:44AM
Java 8 will replace String with String2, which will treat empty string and null the same.
A percentile is the value of a variable below which a certain percent of observations fall. So the 20th percentile is the value (or score) below which 20 percent of the observations may be found.
The 25th percentile is also known as the first quartile; the 50th percentile as the median.
SELECT SUBSTRING_INDEX(
SUBSTRING_INDEX(
GROUP_CONCAT( -- 1) make a sorted list of values
f.length
ORDER BY f.length
SEPARATOR ','
)
, ',' -- 2) cut at the comma
, 90/100 * COUNT(*) + 1 -- at the position beyond the 90% portion
)
, ',' -- 3) cut at the comma
, -1 -- right after the desired list entry
) AS `90th Percentile`
FROM sakila.film AS f
90
represents which percentile we want, that is, "the 90th percentile".SEPARATOR ','
bit, as the default separator is a comma anyway. I just wanted to have a clear indication for the source of the ','
arguments in the SUBSTRING_INDEX()
calls)GROUP_CONCAT()
to create an ordered list of values. Then we use the substring variation SUBSTRING_INDEX()
to find and excise a list entry at a particular desired position.
N / 100
N / 100 * COUNT(*)
N / 100 * COUNT(*) + 1
+-----------------+
| 90th Percentile |
+-----------------+
| 173 |
+-----------------+
173
we see:
mysql> SELECT 100 * COUNT(IF(f.length < 173, 1, NULL))/COUNT(*) `Percentage`
-> FROM film AS f;
+------------+
| Percentage |
+------------+
| 89.4212 |
+------------+
mysql> SELECT title FROM film WHERE length = 173;
+----------------------+
| title |
+----------------------+
| BALLROOM MOCKINGBIRD |
| CONQUERER NUTS |
| FIRE WOLVES |
| GLADIATOR WESTWARD |
| PIZZA JUMANJI |
| TALENTED HOMICIDE |
| VELVET TERMINATOR |
+----------------------+
7 rows in set (0.01 sec)
NULL
values. Currently this method does not work when the column for which you want to caculate percentile values is nullable. It is possible to work around this though. If you can exclude the rows with the NULL
value entirely, you can simply add a WHERE
clause. This is a good idea also because it will cull the number of rows to process. SELECT
list that needs to do something with all rows. You can then still work around it, with some extra hassle. It would involve tweaking the GROUP_CONCAT
to ignore NULL values. This could be done like this:
GROUP_CONCAT(
IF(<column> IS NULL
, ''
, <column>)
ORDER BY <column>
SEPARATOR ','
)
GROUP_CONCAT()
does not also return NULL
when a NULL
value is present in the specified column. If there are NULL
values, these will end up as a list of comma's in the head of the result:
,,,,<non-null-value1>,...,<non-null-valueN> -- 4 NULL values
NULL
's (and we do) we can clean up our list easily with just SUBSTRING()
:
SUBSTRING(
GROUP_CONCAT(
IF(<column> IS NULL
, ''
, <column>)
ORDER BY <column>
SEPARATOR ','
)
, SUM(IF(<column> IS NULL, 1, 0)) + 1
)
COUNT(*)
we should use COUNT(<column>)
in order to not count the NULL
values.group_concat_max_len
GROUP_CONCAT()
, an issue that should always be on your radar is the maximum length of the GROUP_CONCAT()
result. If the result value exceeds the maximum length, the GROUP_CONCAT()
result will be truncated, and a warning will be issued:
1 row in set, 1 warning (0.00 sec)
mysql> show warnings;
+---------+------+--------------------------------------+
| Level | Code | Message |
+---------+------+--------------------------------------+
| Warning | 1260 | 1 line(s) were cut by GROUP_CONCAT() |
+---------+------+--------------------------------------+
GROUP_CONCAT()
result messes up the entire calculation.GROUP_CONCAT()
result is controlled through the group_concat_max_len
system variable.
SET @@group_concat_max_len := <num-bytes>
max_allowed_packet
system variable. This means you can write:and you will never be bothered by this problem again. The
SET @@group_concat_max_len := @@max_allowed_packet;
GROUP_CONCAT()
result can still be too large though (namely, larger than the maximum packet size) but in that case you will get a proper error instead of a truncated result.group_concat_max_len
to a high value may lead to memory problems, as each GROUP_CONCAT()
invocation may individually reserve the specified amount of memory to deal with its result.PRIMARY KEY
and UNIQUE
constraints are unique indexesWrong - an index is just a convenient implementation to detect duplicate entries, and this is used by all RDBMS-es I am familiar with to implement PRIMARY KEY
and UNIQUE
constraints. However, the fact that there is a distinction is evident in for example the Oracle SQL syntax. For example, in ALTER TABLE ... DROP CONSTRAINT
you can specify whether the associated index should be kept or also discarded.
Some people argue that it does not make sense to make the distinction in case the RDBMS does not maintain the constraint and index as separate objects. (This is the case in for example MySQL.)
Well, maybe...but I disagree. When I think about constraints, I'm thinking about business rules and guarding them to maintain database integrity. When talking about indexes, I'm thinking about performance and access paths. Quite different things, and in my opinion a shame to throw away the words to express the difference in my opinion.
No - there is nothing wrong with an empty table. In other words, it does not consist of rows. It may or may not contain rows, but that is a different story.
Wrong - first of all, a scalar subquery may return zero rows, in which case it evaluates to null, which is perfectly valid. But there is more to it.
Whether something is or is not a subquery is matter of syntaxis. The SQL grammer is defined so that if you encounter a query between parenthesis where a scalar value is appropriate, then that query (including the parentheses) will be parsed as a scalar subquery. In other words, the text satisfies the production rule for the non-terminal symbol "scalar subquery".
The parser will usually be smart enough to verify whether the subquery yields one column, but the number of rows returned is a runtime affair.
Suppose the query that makes up the scalar subquery would in fact return more than one row...would it suddenly not be a scalar subquery anymore? Of course not. It is still a scalar subquery - it just happens to be impossible to execute it. In other words, it violates the semantics of a scalar subquery and is therefore invalid. But the mere fact that we can conlcude that must imply that it is a scalar subquery.
SELECT
statement that appears as a part of another SELECT
statementWrong - For the same reasons as the previous issue. A statement is a syntactical construct. It has to do with discovering a pattern in a piece of text so that it satisfies a particular rule in the SQL grammer. That grammar does not have a rule that allows statements to be nested - not in pure SQL anyway (Of course, in stored procedures, one can have statement blocks like BEGIN...END
, IF...END IF
etc that really can contain other statements)
Of course, if we would take the SELECT
that makes up the subquery and run it in isolation, it would be a SELECT
-statement. Bit that is exactly the heart of the matter: because we are regarging it as part of another statement, it cannnot be a statement itself. This is simply a matter of definition of course - most people will immediately understand what is meant.
What would be better to say though is that a subquery is a query or query expression that appears as part of another SQL statement. However, this is also not correct: CREATE VIEW
for example does contain a query expression, but this would most likely not be called a subquery. For this particular case, you can argue that there is nothing sub-ish about the query expression, because it is simply an essential part of the CREATE VIEW
statement.
But what to think of CREATE TABLE...AS SELECT...
and INSERT INTO...SELECT
? The query expression is certainly not an essential part of CREATE TABLE
and INSERT INTO
, and in that sense, the query does look like it is subordinate to the statement it is part of.
You could argue that a query is a subquery if it appears inside another query. That seems sound, but what to think of UPDATE ... SET = (SELECT ...)
? Personally I am reluctant to call an UPDATE
statement a query - I tend to think of a query as a SELECT
statement or sometimes a query expression
.
I can think of only one thing that really is a defining characteristic of a subquery though - that is that the query expression must appear within parentheses. So, again, a matter of syntax more than a matter of semantics. I must admit I'm still not very satisfied with this though...What do you think?
NULL
is the absence of a valueVariants of this statement go like "NULL
is a missing value" or "NULL
is not a value".
With slight doubt, I say: wrong. It certainly is true that many people use NULL
to convey that something is not there or that something is not applicable. But this is a matter of choice, it does not change the meaning of NULL
itself. If we use the same line of reasoning as we used for the subquery myth, we must conclude that NULL
is certainly a valid value expression. It can legally appear anywhere where we can put a value. It is IMO also perfectly ok to say things like "...that expression evaluates to NULL
".
So what does the SQL standard say? Well, here's a quote:
...the null value is neither equal to any other value nor not equal to any other value — it is unknown
whether or not it is equal to any given value....
So, I'm in that camp too: NULL
is a value, and if we have a NULL
in say, the integer domain, we just don't know which of all possible integers it is.
Wrong - a Unique constraint is mostly just as acceptable.
In MySQLs InnoDB it is even more relaxed - the foreign key only needs to reference the prefix of an index in the parent table, although this is so exotic, it should probably be ignored.
Wrong - a table is normalized when it is in the first Normal form. There are a few different opinions what that means exactly, but it usually works to say that a table is not normalized when it contains repeating groups.
A slightly stronger statement is to say that a table is not normalized when it contains data that is not atomic. This is stronger because it does not cover only repeating groups, but also columns that, for a single row, do not contain a single value. For example, a first name/last name combination in one column is not atomic, and therefore, a table that contains such values is not normalized. (There are opinions that require even more than this, but for practical purposes the sense of atomic values works pretty well.)
The source of confusion is in what happens beyond the first normal form. Although a table maybe normalized, it can still contain redundancy. By removing redundancy, you can progressively achieve a higher normal form. In many cases, one would require at least third normal form or the Boyce-Codd normal form for building database schemas. Many people say "normalized" when they actually mean "in at least the third normal form".
The DataZen winter meetup 2025 is nigh! Join us 18 - 20 February 2025 for 3 days of expert-led sessions on AI, LLM, ChatGPT, Big Data, M...