2

我有三张桌子:

`MEMBERS`
with
`NAME` varchar(24) UNIQUE KEY

`LAST_LOGGED_IN` int(11) - It is a timestamp!

`HOMES`
with
`OWNER` varchar(24) 

`CARS`
with
`OWNER` varchar(24)

我对这些表使用 InnoDB,现在我的实际问题是:如果 UNIX_TIMESTAMP()- ,我如何删除所有表中的行MEMBERSLAST_LOGGED_IN> 864000?

我正在尝试删除非活动成员的行,这是迄今为止最难的事情。我有大约 40K 行,并且还在增加。我经常用DELETE FROM MEMBERS WHERE UNIX_TIMESTAMP()-LAST_LOGGED_IN> 864000

您的任何帮助将不胜感激!谢谢!!

4

2 回答 2

1

我不使用 InnoDB,所以我不得不查找它,但它似乎支持参照完整性。如果您设置关系然后打开 DELETE CASCADE,则数据库本身将执行规则……即,当您删除成员时,DBMS 将负责删除关联的 Homes 和 Cars。

这里这里,他们可能会有所帮助。

于 2012-12-23T03:33:48.360 回答
1

如果您已经从MEMBERS表中删除了行,并且您想从其他两个表中删除列的值与表中任何行的值OWNER都不匹配的行:NAMEMEMBERS

DELETE h.*
  FROM `HOMES` h
  LEFT
  JOIN `MEMBERS` m 
    ON m.`NAME` = h.`OWNER`
 WHERE m.`NAME` IS NULL

DELETE c.*
  FROM `CARS` c
  LEFT
  JOIN `MEMBERS` m 
    ON m.`NAME` = c.`OWNER`
 WHERE m.`NAME` IS NULL

(注意,这些语句还将从列中删除行,HOMES并将CARSOWNER作为 NULL 值。)

我强烈建议您在运行 DELETE 之前使用 SELECT 运行这些语句的测试。(将关键字DELETE替换为关键字SELECT,即

-- DELETE h.*
SELECT h.*
  FROM `HOMES` h
  LEFT
  JOIN `MEMBERS` m 
    ON m.`NAME` = h.`OWNER`
 WHERE m.`NAME` IS NULL

展望未来,如果您想保持这些表“同步”,您可以考虑使用 ON CASCADE DELETE 选项定义 FOREIGN KEY 约束。

或者,您可以使用删除所有三个表中的行的 DELETE 语句:

DELETE m.*, h.*, c.*
  FROM `MEMBERS` m
  LEFT
  JOIN `HOMES` h
    ON h.`OWNER` = m.`NAME`
  LEFT
  JOIN `CARS` c
    ON c.`OWNER` = m.`NAME`
 WHERE UNIX_TIMESTAMP()-m.`LAST_LOGGED_IN` > 864000

(N.B. the predicate there cannot make use of an index on the LAST_LOGGED_IN column. An equivalent predicate with a reference to the "bare" column will be able to use an index.

WHERE m.`LAST_LOGGED_IN` < UNIX_TIMESTAMP()-864000

or an equivalent:

WHERE m.`LAST_LOGGED_IN` < UNIX_TIMESTAMP(NOW() - INTERVAL 10 DAY)

For best performance, you would need indexes on both HOMES and CARS with a leading column of OWNER, e.g.

... ON `HOMES` (`OWNER`)
... ON `CARS` (`OWNER`) 
于 2012-12-23T04:08:55.083 回答