1

作成中の Web サイト用に作成した、従業員のリストを含むデータベースがあります。各従業員の写真、名前、電話番号などを含むグリッドのようなリストになります。

これは私の最初のデータベース設計であり、私はそれを本当に誇りに思っています...しかし、私は初心者なので、いくつかの点で非効率的であると確信しています.

ウェブサイトが要素を作成するためにクエリを実行する最良の方法を見つけるのに苦労しています。

1) 仮想テーブルを使用する必要がありますか? それとも、1 つのクエリを使用して、従業員ごとにループする必要がありますか?

2) 一部の従業員は、複数の管轄権を持ちます。今私は持っています:

select employees.firstName, employees.lastName, employees.phone, employees.position,
    employees.picture, jurisdictions.jurisdiction
from employees
    inner join(jurisdictions cross join departments cross join user_jurisdictions)
    on (employees.deptID = departments.deptID
        AND user_jurisdictions.userID = employees.userID
        AND user_jurisdictions.jurID = jurisdictions.jurID)

どちらが返されますか:

+-----------+----------+--------------+-----------------+---------+--------------+
| firstName | lastName | phone        | position        | picture | jurisdiction |
+-----------+----------+--------------+-----------------+---------+--------------+
| John      | Smith  | 210-226-3232 | Senior Manager   |/pics/jpeg1|South America|
| John      | Smith  | 210-226-3232 | Senior Manager   |/pics/jpeg1|London       |
+-----------+----------+--------------+-----------------+---------+--------------+

従業員が追加の管轄権を持つため、重複行を削除するクエリを作成する方法はありますか? 何かのようなもの?

+-----------+----------+--------------+---------+---------+--------------+------------+
| firstName | lastName | phone        | position| picture | jurisdiction |Jurisdiction|
+-----------+----------+--------------+---------+---------+--------------+------------+
| John      | Smith  | 210-226-3232 | Manager |/pics/jpeg1| South America|London      |
+-----------+----------+--------------+-----------------+---------+-------------------+

これが私のmysqlスキーマです:

employees
--------------------
userID (primary key)
firstName
lastName
phone
fax
position
picture
deptID (foreign key references departments(deptID)) 



departments
--------------------
deptID (primary key)
department

jurisdictions
-----------------
jurID (primary key)
jurisdiction


user_jurisdictions
--------------------------
userID(foreign key references employees(userID)) 
jurID(foreign key references jurisdictions(jurID))


triger: 
 after_employees_insert | INSERT | employees | begin
insert into user_jurisdictions(userID) values (new.userID);
4

1 に答える 1

3

結果を従業員別にグループ化し、MySQL のGROUP_CONCAT()関数を使用して従業員の管轄区域を集計できます。

SELECT   employees.firstName,
         employees.lastName,
         employees.phone,
         employees.position,
         employees.picture,
         GROUP_CONCAT(jurisdictions.jurisdiction)
FROM     employees
    JOIN departments        USING (deptID)
    JOIN user_jurisdictions USING (userID)
    JOIN jurisdictions      USING ( jurID)
GROUP BY employees.userID

ただし、これは管轄区を区切られた文字列に集約します (これにより、複数の管轄区と区切り文字を含む単一の管轄区を区別することが難しくなります: 管轄区名で使用される可能性が低い区切り文字を選択できますが、それでも次のような問題が発生する可能性があります。文字列の長さの制限として、私の見解では、基本的に怠惰です)。

より良い方法は、このような集計をアプリケーション コードの上位レベルに任せることです。たとえば、PDOを使用すると:

$dbh = new PDO("mysql:dbname=$dbname", $username, $password);

$qry = $dbh->query('
  SELECT   employees.userID
           employees.firstName,
           employees.lastName,
           employees.phone,
           employees.position,
           employees.picture,
           jurisdictions.jurisdiction
  FROM     employees
      JOIN departments        USING (deptID)
      JOIN user_jurisdictions USING (userID)
      JOIN jurisdictions      USING ( jurID)
  ORDER BY employees.userID
');

$row = $qry->fetch();
while ($row) {
  $current_user = $row['userID'];

  // handle $current_user initialisation
  do {
    // handle user $row
  } while ($row = $qry->fetch() and $row['userID'] == $current_user);
  // handle $current_user termination

}

もちろん、これには、RDBMS によって生成され、上位レベルのコードに転送/処理する必要がある、はるかに大きな結果セットが生成されるという欠点があります。

于 2012-12-19T21:35:42.993 に答える