0

タイトルがわかりにくいのでごめんなさい。悲しいことに、テキストはさらに混乱しています。

基本的に、あるテーブルから別のテーブルにデータをインポートするSQLスクリプトがあり、特定の行を無視しようとしています。

最初のテーブルは「イベント」ごとに3つの行を記録しており、そのうちの1つだけが必要です。無視したいイベントは2つのほぼ重複していますが、1つの列は1ではなく0であり、時間も異なる可能性があります。まだ一致するように20秒の制限を与えています。

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

INSERT INTO prism_actions (action_time, action_type, player, world, x, y, z, data)
  SELECT FROM_UNIXTIME(`co_blocks`.time), 
    'block-shift', 
    'Piston', 
    CASE WHEN `co_blocks`.wid = 1 THEN 'world' ELSE (CASE WHEN `co_blocks`.wid = 2 THEN 'world_nether' ELSE 'world_the_end' END) END, 
    SUBSTRING_INDEX( `co_blocks`.bcords , '.', 1 ), -- This will get the X coordinate of this action
    SUBSTRING_INDEX(SUBSTRING_INDEX( `co_blocks`.bcords , '.', 2 ),'.', -1), -- Y coordinate
    SUBSTRING_INDEX(SUBSTRING_INDEX( `co_blocks`.bcords , '.', 3 ),'.', -1), -- Z
    CONCAT("{\"block_id\":", `co_blocks`.type, ",\"block_data\":", `co_blocks`.data, "}")
  FROM `co_blocks`
  WHERE `co_blocks`.user LIKE '#piston' 
    AND `co_blocks`.action = 1 
    AND NOT (EXISTS(
      SELECT `id` FROM `co_blocks` WHERE user LIKE '#piston' AND action = 0 AND time < (`co_blocks`.time + 20) AND time > (`co_blocks`.time - 20) AND `co_blocks`.bcords LIKE bcords))
  ORDER BY id ASC;

ステートメントのEXISTS()中には、ほぼ重複したレコードがあるかどうかを確認しようとしているものがあります。WHERE

私の問題は、最初の列のco_blocks時間をチェックするために.timeを使用していることです。SELECT最初の時間を使うのか、2番目の時間を使うのかわかりませんSELECT

SELECT `id` 
FROM `co_blocks` 
WHERE user LIKE '#piston' 
AND action = 0 
AND time < (`co_blocks`.time + 20) 
AND time > (`co_blocks`.time - 20) 
AND `co_blocks`.bcords LIKE bcords

同じテーブル名を使用しています。2番目のaをチェックインするために最初のデータをどのように使用しますか?SELECTWHERESELECT

編集: これが私が始めたいくつかのサンプルデータです:

+------+------+------+------------+---------+------------+------+------+--------+------+------+
| id   | cx   | cz   | time       | user    | bcords     | type | data | action | rb   | wid  |
+------+------+------+------------+---------+------------+------+------+--------+------+------+
| 2147 |   22 |   17 | 1361130494 | #piston | 359.67.276 |    3 |    0 |      1 |    0 |    1 |
| 2148 |   22 |   17 | 1361130494 | #piston | 359.67.276 |    3 |    0 |      0 |    0 |    1 |
| 2149 |   22 |   17 | 1361130494 | #piston | 358.67.276 |    3 |    0 |      1 |    0 |    1 |

最後の行のデータのみをインポートしたい(bcordが異なり、action = 1)

編集2:

私はこれについてもっと文脈を与えるべきです。co_blocksあるテーブルからデータを取得し、それを別のテーブルに配置しようとしていますprism_actions。を使用するプログラムはprism_actions、このアクションに1つの行のみを使用しますが、を使用するプログラムco_blocksは3を使用します。私は、から正しいアクションを取得して、に入れようとしていco_blocksますprism_actions

編集3:

これが私が問題を抱えている別の例です。うまくいけば、それが理解しやすくなるでしょう。私のテーブルには値があり、各テーブルの情報を相互に比較する2つのステートメントが必要です。

UPDATE co_pistons
    SET x = (SELECT SUBSTRING_INDEX( bcords , '.', 1 ) FROM `co_pistons` WHERE 
    `co_pistons`.bcords LIKE bcords
    LIMIT 1)
    WHERE NOT isFrom;

この3行目で、co_pistons.bcordsとbcords同じものを参照しています。co_pistons.bcordsが' sbcordを参照するようにしたいUPDATEので、それらを相互に比較できます。

4

1 に答える 1

0

As a solution for this, I ended up creating a separate table, and adding in all the data I needed to use. Then, I could compare the table's data in a subquery to the main query's data. I'm not sure if this is too efficient, but for my script it works fine for me, as the script is only run once. If anyone has any better ideas that would be great, but otherwise this works for me.

EDIT

My issue was actually that I didn't know how to use AS to name tables differently. This was causing me to have two tables used in the query with the same name, which ended up confusing me. The solution is to name the tables with nicknames:

FROM `co_blocks` as c1
...
SELECT `co_blocks` as c2 WHERE c1.bcords = c2.bcords

The previous solution works, I suppose, but it's definitely not the best way to do it.

于 2013-02-18T17:54:28.327 に答える