ですから、SQL は開発者としての私の最も弱い面だと言わざるを得ません。おそらく、私が達成しようとしていることはかなり簡単です。私はこのようなものを持っています (これは実際のモデルではありませんが、説明に時間を浪費することなく理解しやすくするために、使用する必要があるテーブルの関係を正確に模倣する例を考え出しました)。一方では、テーブルを「ユーザー」と呼びましょう。主キー「UserId」、「UserName」などの列。
次に、別の表「ライセンス」です。ユーザーと 1:N で関連付けます。各ライセンスは 1 人のユーザーに属し、ユーザーは複数のライセンスを持つことができます。したがって、PK IdLicense、FK IdUser などがあります。
続いて「Equipments」というテーブル。ここでは、さまざまな機器を定義しています。IdEquipment、EquipmentName. それについては、これ以上言うことはありません。
最後に、「ライセンス」と「機器」の間の N:M 関係を作成するテーブル。ユーザーは、ライセンスを定義するときに、ライセンスで操作できるさまざまな機器を指定できます。したがって、ライセンスは複数の機器に関連付けることができ、機器の一部は複数のライセンスに関連付けることができます。
本当の取引はここに来ます。装備の取り扱い資格をもとにユーザーを絞り込める何らかの検索システムの実装を命じられた。 "、"B"、"C"。たとえば、James と Dave の 2 人のユーザーがいるとします。James には 2 つのライセンスがあり、Dave には 1 つのライセンスがあります。James は、最初のライセンスでマシン "A" と "D" を使用する資格があり、2 番目のライセンスで "B" と "C" を使用する資格があります。Dave は、彼の唯一のライセンスで、機器タイプ "B" および "C" を処理する資格があります。機器「A」、「B」、および「C」を処理できるユーザーを誰かが検索しようとすると、返されるレコードは James だけになります。
これまでのところ、次のようなことをしなければならないと思っていました
SELECT DISTINCT IdUser
FROM Users
INNER JOIN Licenses
ON Licenses.IdUser = Users.idUser
INNER JOIN LicensesEquipments
ON LicensesEquipments.IdLicense = Licenses.IdLicense
INNER JOIN Equipment
ON Equipment.IdEquipment = LicensesEquipments.IdEquipment
WHERE Equipment.IdEquipment = ??
「A」「B」および「C」の 3 つの異なる idEquipments すべてでこれをフィルタリングするにはどうすればよいですか? 明らかに、セルが 2 つの異なる値に等しくならないため、WHERE Equipment.IdEquipment = 1 と Equipment.IdEquipment = 2 を作成することはできません。WHERE Equipment.IdEquipment = 1 または Equipment.IdEquipment = 2 も実行できません。OR を使用すると、可能性の少なくとも 1 つを保持しているユーザーが有効な結果と見なされるため、3 つすべてを持つユーザーを探しています。この場合のさまざまな機器。
最初は、エイリアスを使用して、テーブル機器で複数の内部結合を作成し、機器のフィルターと同じ回数それを行い、各エイリアスを異なるフィルターで使用する必要があると想定しました。しかし、その後、私のコードスーパーバイザーがやって来て、それを忘れるように言いました。なぜなら、彼は、フィルターを追加するとコストがかかりすぎると言ったからです (ただし、彼はより良い代替手段を提供しませんでした...)