Если A
является ключом в fish
, то любая проекция только на рыбу создаст набор результатов, где А все еще уникален.
Соединение между таблицей fish и любой таблицей с соотношением 1: 1 (например, fish_type) даст набор результатов, в котором A уникален.
Соединение с другой таблицей, имеющей отношение 1: M или M: M от fish (например, fish_beits), НЕ даст результата, в котором A уникален, если только вы не предоставите предикат фильтра на «другой» стороне (такой как bait='Dynamite'
).
SELECT * FROM (SELECT * FROM FISH) D, (SELECT * FROM FISH2) E WHERE D.A = E.A
... логически эквивалентно следующему утверждению, и большинство баз данных (включая MySQL) выполнят преобразование:
select *
from fish
join fish2 on(fish.a = fish2.a)
Является ли A все еще уникальным в наборе результатов, зависит от ключа fish2
и их отношения (см. Выше).
Конкатенация не сохраняет уникальность. Рассмотрим следующий случай:
concat("10", "10") => "1010"
concat("101", "0") => "1010"
Следовательно, ваш последний запрос ...
SELECT *
FROM (SELECT CONCAT(A,B) AS DUCK, C FROM FISH) D
,(SELECT CONCAT(A,B) AS DUCK2, C FROM FISH2) E
WHERE D.DUCK = E.DUCK2
... не будет (обязательно) давать тот же результат, что и
select *
from fish
join fish2 on(
fish.a = fish2.a
and fish.b = fish2.b
)
Я написал обязательно , потому что коллизии зависят от фактических значений. Некоторое время назад я выискивал ошибку, в которой именно эта причина и была. Код работал несколько лет, пока ошибка не проявилась.