Sqlserver
 sql >> база данни >  >> RDS >> Sqlserver

SQL обобщената таблица е само за четене и клетките не могат да се редактират?

Ако приемем, че имате уникално ограничение за n_id, field което означава, че най-много един ред може да съвпадне, можете (поне на теория) да използвате INSTEAD OF спусък.

Това би било по-лесно с MERGE (но това не е налично до SQL Server 2008), тъй като трябва да покриете UPDATES на съществуващи данни, INSERTS (Където NULL стойността е зададена на NON NULL едно) и DELETES където NON NULL стойността е зададена на NULL .

Едно нещо, което трябва да обмислите тук, е как да се справите с UPDATES които задават всички колони в един ред на NULL Направих това по време на тестването на кода по-долу и бях доста объркан за минута или две, докато разбрах, че това е изтрило всички редове в основната таблица за n_id (което означаваше, че операцията не е била обратима чрез друго UPDATE изявление). Този проблем може да бъде избегнат чрез дефиницията на VIEW OUTER JOIN върху коя и да е таблица n_id е ПК на.

Пример за типа нещо е по-долу. Ще трябва също да вземете предвид потенциални условия на състезание в INSERT /DELETE посочен код и дали имате нужда от допълнителни съвети за заключване там.

CREATE TRIGGER trig
ON pivoted
INSTEAD OF UPDATE
AS
  BEGIN
      SET nocount ON;

      DECLARE @unpivoted TABLE (
        n_id             INT,
        field            VARCHAR(10),
        c_metadata_value VARCHAR(10))

      INSERT INTO @unpivoted
      SELECT *
      FROM   inserted UNPIVOT (data FOR col IN (fid, sid, NUMBER) ) AS unpvt
      WHERE  data IS NOT NULL

      UPDATE m
      SET    m.c_metadata_value = u.c_metadata_value
      FROM   metadata m
             JOIN @unpivoted u
               ON u.n_id = m.n_id
                  AND u.c_metadata_value = m.field;

      /*You need to consider race conditions below*/
      DELETE FROM metadata
      WHERE  NOT EXISTS(SELECT *
                        FROM   @unpivoted u
                        WHERE  metadata.n_id = u.n_id
                               AND u.field = metadata.field)

      INSERT INTO metadata
      SELECT u.n_id,
             u.field,
             u.c_metadata_value
      FROM   @unpivoted u
      WHERE  NOT EXISTS (SELECT *
                         FROM   metadata m
                         WHERE  m.n_id = u.n_id
                                AND u.field = m.field)
  END  


  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Защо моите диаграми в SSRS 2012 не се показват?

  2. Преобразуването на C# datetime в sql server datetime извежда грешка

  3. COS() Примери в SQL Server

  4. Съвети за коригиране на фрагментацията на индекса на SQL Server

  5. Database Tuning Advisor препоръчва да се създаде съществуващ индекс