Oracle 11g-合并和错误ORA-30926:无法在源表中获得稳定的行集

时间:2018-08-06 17:34:39

标签: sql oracle oracle11g merge

我已经阅读了很多有关Oracle(11g)错误ORA-30926的帖子,并且我已经查看了Oracle的文档,了解如何正确使用merge语句。

基于先前的线程,我更改了代码以在using子句中指定一个不同的值,这就是我在ON子句中比较的值。但是我仍然收到ORA-30926错误。

我还在USING子句中测试了子查询,它返回数据没有任何问题。我创建了一个临时表,该表仅包含满足USING语句的WHERE子句中的条件的数据,并尝试运行该表,但仍然出现错误。两个表中都有数据。

我希望有人可以在我的代码中发现不正确的地方,或者给我有关测试的任何建议。

BEGIN
MERGE 
INTO persons myTarget
USING (
    select 
      distinct(USERID),
      GIVENNAME,
      INITIALS,
      SN,
      GENERATIONQUALIFIER,
      TITLE,
      DISPLAYNAME,
      TELEPHONENUMBER,
      FACSIMILETELEPHONENUMBER,
      MOBILE,
      OTHERTELEPHONE
    from person_updates
    WHERE
      SN IS NOT NULL
      AND LENGTH(SN) < 20
      AND SUBSTR(USERID,0,2) IN (SELECT PLACEID FROM code_table)
      AND (LENGTH(USERID) = 8 OR LENGTH(USERID) = 10)
  ) mySource
  ON (myTarget.userid = mySource.USERID)
WHEN MATCHED THEN
    UPDATE SET myTarget.first_name = UPPER(mySource.GIVENNAME),
    myTarget.last_name = UPPER(mySource.SN),
    myTarget.generation = UPPER(mySource.GENERATIONQUALIFIER),
    myTarget.title = UPPER(mySource.TITLE),
    myTarget.display_name = UPPER(mySource.DISPLAYNAME),
    myTarget.phone_num = UPPER(mySource.TELEPHONENUMBER),
    myTarget.fax_num = UPPER(mySource.FACSIMILETELEPHONENUMBER),
    myTarget.mobile_num = UPPER(mySource.MOBILE),
    myTarget.dsn_phone = UPPER(mySource.OTHERTELEPHONE);
END;

1 个答案:

答案 0 :(得分:0)

@shrek正确地指出,使用distinct将为您跨所选所有列的组合提供不同的行。我已经使用row_number分析函数仅根据用户ID获得不同的行。

查询:

BEGIN
MERGE 
INTO persons myTarget
USING (
    select * from(
    select 
      row_number() over(partition by userid order by null) as rn,
      USERID,
      GIVENNAME,
      INITIALS,
      SN,
      GENERATIONQUALIFIER,
      TITLE,
      DISPLAYNAME,
      EMPLOYEETYPE,
      TELEPHONENUMBER,
      FACSIMILETELEPHONENUMBER,
      MOBILE,
      OTHERTELEPHONE
    from person_updates
    WHERE
      SN IS NOT NULL
      AND LENGTH(SN) < 20
      AND SUBSTR(USERID,0,2) IN (SELECT PLACEID FROM code_table)
      AND (LENGTH(USERID) = 8 OR LENGTH(USERID) = 10)) where rn = 1
  ) mySource
  ON (myTarget.userid = mySource.USERID)
WHEN MATCHED THEN
    UPDATE SET myTarget.first_name = UPPER(mySource.GIVENNAME),
    myTarget.last_name = UPPER(mySource.SN),
    myTarget.generation = UPPER(mySource.GENERATIONQUALIFIER),
    myTarget.title = UPPER(mySource.TITLE),
    myTarget.display_name = UPPER(mySource.DISPLAYNAME),
    myTarget.dod_emp_type = UPPER(mySource.EMPLOYEETYPE),
    myTarget.phone_num = UPPER(mySource.TELEPHONENUMBER),
    myTarget.fax_num = UPPER(mySource.FACSIMILETELEPHONENUMBER),
    myTarget.mobile_num = UPPER(mySource.MOBILE),
    myTarget.dsn_phone = UPPER(mySource.OTHERTELEPHONE);
END;  

希望这会有所帮助。