0

プラットフォームと一緒に名前の重複を見つけることを目的としたコードのビットに問題があります。これは、後で一意のIDを見つけるためにも適用されます。

したがって、たとえば、Xboxに「Apple」という名前のサーバーがあり、同じプラットフォームで「Apple」という名前のレコードを挿入しようとすると、そのサーバーは拒否されます。ただし、PS3の「Apple」など、同じ名前の別のプラットフォームは許可されます。

私はアイデアを考え出し、答えを探してみましたが、重複をチェックするための最善の方法については、ちょっと暗闇の中にいます。

これまでのところ、これは私が持っているものです:

$nameDuplicate_sql = $db->prepare("SELECT * FROM `servers` WHERE name=':name' AND platform=':platform'");
$nameDuplicate_sql->bindValue(':name', $name);
$nameDuplicate_sql->bindValue(':platform', $platform);
$nameDuplicate_sql->execute();

私はたくさんの異なる解決策を試しました。いくつかはここから、他はPHPのマニュアルなどからです。しかし、どれもうまくいかないようです。

私はPDOに固執しようとしていますが、これはどこを向いたらよいかわからない1つの例です。これがmysql_*にある場合、おそらくmysql_affected_rowsを使用できますが、PDOでは手がかりがありません。rowCountは有望に見えましたが、これはINSERT、UPDATE、またはDELETEステートメントではないため、常に0を返します。

ああ、phpMyAdminでSQLステートメントを試しましたが、機能します。単純な名前/プラットフォームで試してみたところ、行が正しく見つかりました。

誰かがここで私を手伝ってくれるなら、私はそれをいただければ幸いです。

4

3 に答える 3

2

ほとんどのデータベースでは、PDOStatement :: rowCount()はSELECTステートメントの影響を受ける行数を返しません。代わりに、PDO :: query()を使用して目的のSELECTステートメントと同じ述語でSELECT COUNT(*)ステートメントを発行し、次にPDOStatement :: fetchColumn()を使用して返される行数を取得します。その後、アプリケーションは正しいアクションを実行できます。

于 2012-09-05T02:20:12.330 に答える
2

重複をチェックする代わりに、データベーステーブルに直接適用しないのはなぜですか?エントリがすでに存在する場合にエントリの作成を禁止する複合キーを作成しますか?

CREATE TABLE servers (
    serverName varchar(50),
    platform varchar(50),
    PRIMARY KEY (serverName, platform)
) 

このようにすると、重複が発生することinsert... on duplicate key update...はなく、mysql構文を使用することもできます。これはかなり便利なようです。

すでに主キーが設定されている場合、または新しいテーブルを作成したくない場合は、次を使用できます。

ALTER TABLE servers DROP PRIMARY KEY, ADD PRIMARY KEY(serverName, platform);

編集:主キーは、単一の行または複数の行のいずれかであり、一意のデータが含まれている必要があります1つの行に同じ値を2回含めることはできませんが、複合キー(ここで提案しているもの)は、2つの列の間に同じデータを表示できないことを意味します。

この場合、あなたがしたいことは、サーバー名を追加し、それをプラットフォームに関連付けます-テーブルは、それぞれがに関連付けられた一意のプラットフォームを持っている限り、同じサーバー名を含む行をいくつでも追加できます逆に、すべてのサーバー名が一意である限り、プラットフォームを何度でもリストすることができます。

同じサーバー名/プラットフォームの組み合わせが存在する場所にレコードを挿入しようとすると、データベースはそれを許可しません。ただし、もう1つの大きなメリットがあります。このキーの制約により、mysqlでは特別なタイプのクエリを使用できます。insert... on duplicate key update構文です。つまり、同じデータを2回挿入しようとすると(つまり、データベースに「いいえ」と表示された場合)、そのデータをキャッチして、テーブルに既にある行を更新できます。例えば:

の行がserverName=Fluffehあり、それはオンにplatform=Booshなっていますが、現時点ではそれについて知らないため、サーバーのIPアドレスを更新する目的でレコードを挿入しようとします。

通常、次のように記述します。

insert into servers (serverName, platform, IPAddress) 
values ('$serverName', '$platform', '$IPAddy')

しかし、識別された優れた主キーを使用して、これを行うことができます。

insert into servers (serverName, platform, IPAddress) 
values ('$serverName', '$platform', '$IPAddy') 
on duplicate key update set IPAddress='$IPAddy';

2番目のクエリは、データがまだ存在しない場合は、すべてのデータを含む行を挿入します。もしそうなら、バム!それはずっとあなたの意図であったサーバーのIPアドレスを更新します。

于 2012-09-05T02:21:24.857 に答える
1

パラメータトークンのクエリから一重引用符を削除します...バインドされると引用符で囲まれます...これがプリペアドステートメントの理由の一部です。

$nameDuplicate_sql = $db->prepare("SELECT * FROM `servers` WHERE name= :name AND platform= :platform");
于 2012-09-05T02:19:27.837 に答える