0

我有一个主表,比如说tbl,它有三列。col1假设我创建了一个表,该表仅显示关于和的组合唯一的第一条记录col2。此类表的 SQL 定义如下:

CREATE TABLE pseudo_view AS SELECT col1, col2, col3 FROM tbl GROUP BY col1 col2

现在我在这个新表中看到了col1和的所有独特组合。col2我更新此表,col3以便更改给定记录。tbl我希望通过影响所有重复记录将其应用回主表。

我知道这在标准视图中是不可能的。但是,有没有办法创建一个依赖表,当它更新时,主表将按照选择机制的定义进行更新?我想要一个解决方案,这样这个伪视图表可以自由地更新和删除它的记录,同时也影响父表。

4

1 回答 1

1

它可以与 pseudo_view 和 tbl 上的一些触发器一起使用

对于 tbl 上的插入、更新和删除,“视图”需要相应地更新。通常这很容易。唯一困难的部分是当您删除最后一对 col1 和 col2 时。

对于 pseudo_table 上的更新和删除,您需要定义 master 上应该更改的内容。

在我的示例中,我选择将 min(3) 作为函数,因此当更新一行时,同一行(曾经具有最小 col3 的行)被更新,并且为 psuedotable 提供了一个新的(可能相同的)值是计算出来的。

当删除一行时, tbl 中的所有行都需要删除,否则它们也会在伪中给出一行(并且刚刚被删除)。

CREATE TABLE tbl (col1 INT, col2 INT, col3 INT);
INSERT INTO tbl VALUES (1, 1, 1), (1, 1, 2), (2, 2, 3), (2, 2, 4);

CREATE TABLE pseudo_view
  AS
    SELECT
      col1,
      col2,
      MIN(col3) AS col3
    FROM tbl
    GROUP BY col1, col2;

DELIMITER //

-- update the row that originally was the min() and make sure that the new row in pseudo is the new min()
CREATE TRIGGER upd_pseudo
BEFORE UPDATE ON
  pseudo_view FOR EACH ROW
  BEGIN
    UPDATE tbl
    SET col3 = NEW.col3
    WHERE col1 = OLD.col1
          AND col2 = OLD.col2
          AND col3 = OLD.col3;

    SET NEW.col3 := (SELECT
                       MIN(col3)
                     FROM tbl
                     WHERE col1 = OLD.col1
                           AND col2 = OLD.col2);

  END //

-- delete all rows in tbl that has this col1 and col2
CREATE TRIGGER del_pseudo
AFTER DELETE ON
  pseudo_view FOR EACH ROW
  BEGIN
    DELETE FROM tbl
    WHERE col1 = OLD.col1 AND col2 = OLD.col2;
  END //

-- update pseudo to make sure it's still true
CREATE TRIGGER upd_tbl
AFTER UPDATE ON
  tbl FOR EACH ROW
  BEGIN
    UPDATE pseudo_view
    SET col3 = (SELECT
                  min(col3)
                FROM tbl
                WHERE col1 = NEW.col1 AND col2 = NEW.col2)
    WHERE col1 = NEW.col1 AND col2 = NEW.col2;
  END//

-- update pseudo to make sure it's still true
CREATE TRIGGER ins_tbl
AFTER INSERT ON
  tbl FOR EACH ROW
  BEGIN
    REPLACE pseudo_view
      VALUES (NEW.col1, NEW.col2, (SELECT
                                     min(col3)
                                   FROM tbl
                                   WHERE col1 = NEW.col1 AND col2 = NEW.col2));
  END//

-- update pseudo to make sure it's still true
CREATE TRIGGER del_tbl
AFTER DELETE ON
  tbl FOR EACH ROW
  BEGIN
    -- todo: add special case when the delete row was the last of that col1/col2-pair
    REPLACE pseudo_view
      VALUES (NEW.col1, NEW.col2, (SELECT
                                     min(col3)
                                   FROM tbl
                                   WHERE col1 = NEW.col1 AND col2 = NEW.col2));
  END//
于 2013-01-02T18:36:37.397 回答