【问题标题】:Oracle11g ORA-01403 No data found using Select IntoOracle11g ORA-01403 使用 Select Into 找不到数据
【发布时间】:2015-12-31 04:59:47
【问题描述】:

我对 Oracle 还是很陌生,但我遇到了一个困扰了几个小时的问题。

样本:

 Create Table Accounts (Id number(10),Balance number(16,3), Status Varchar2(50),Owner_Id number(10));
 Create Table Transactions (Id number(10),Amount number(16,3), Trxn_date date, Account_Id number(10));
 Create Table Owner (Id number(10), Firstname varchar2(50),Lastname varchar2(50));

 Insert Into Accounts(Id,Balance,Status,Owner_Id) Values (1,1000,'OPEN',10);
 Insert Into Accounts(Id,Balance,Status,Owner_Id) Values (2,5000,'CLOSED',11);
 Insert Into Accounts(Id,Balance,Status,Owner_Id) Values (3,1000,'OPEN',12);
 Insert Into Accounts(Id,Balance,Status,Owner_Id) Values (4,5000,'CLOSED',13);
 Insert Into Accounts(Id,Balance,Status,Owner_Id) Values (5,1000,'OPEN',14);
 Insert Into Accounts(Id,Balance,Status,Owner_Id) Values (6,5000,'CLOSED',15);
 Insert Into Accounts(Id,Balance,Status,Owner_Id) Values (7,1000,'OPEN',16);
 Insert Into Accounts(Id,Balance,Status,Owner_Id) Values (8,5000,'CLOSED',17);
 Insert Into Accounts(Id,Balance,Status,Owner_Id) Values (9,1000,'OPEN',18);
 Insert Into Accounts(Id,Balance,Status,Owner_Id) Values (10,5000,'CLOSED',19);
 Insert Into Accounts(Id,Balance,Status,Owner_Id) Values (11,1000,'OPEN',20);
 Insert Into Accounts(Id,Balance,Status,Owner_Id) Values (12,5000,'CLOSED',21);

 Insert Into Owner(Id,Firstname,Lastname) Values (10,'John','TEST1');
 Insert Into Owner(Id,Firstname,Lastname) Values (11,'John','TEST2');
 Insert Into Owner(Id,Firstname,Lastname) Values (10,'John','TEST3');
 Insert Into Owner(Id,Firstname,Lastname) Values (11,'John','TEST4');
 Insert Into Owner(Id,Firstname,Lastname) Values (10,'John','TEST5');
 Insert Into Owner(Id,Firstname,Lastname) Values (11,'John','TEST6');
 Insert Into Owner(Id,Firstname,Lastname) Values (10,'John','TEST7');
 Insert Into Owner(Id,Firstname,Lastname) Values (11,'John','TEST8');
 Insert Into Owner(Id,Firstname,Lastname) Values (10,'John','TEST9');
 Insert Into Owner(Id,Firstname,Lastname) Values (11,'John','TEST10');
 Insert Into Owner(Id,Firstname,Lastname) Values (10,'John','TEST11');
 Insert Into Owner(Id,Firstname,Lastname) Values (11,'John','TEST12');

 Insert Into Transactions(Id,Amount,Trxn_Date,Account_Id) Values (1,10,'02-FEB-2015',5);
 Insert Into Transactions(Id,Amount,Trxn_Date,Account_Id) Values (2,10,'02-APR-2015',5);
 Insert Into Transactions(Id,Amount,Trxn_Date,Account_Id) Values (3,10,'02-JUN-2015',5);
 Insert Into Transactions(Id,Amount,Trxn_Date,Account_Id) Values (4,10,'02-AUG-2015',5);
 Insert Into Transactions(Id,Amount,Trxn_Date,Account_Id) Values (5,10,'02-FEB-2015',2);
 Insert Into Transactions(Id,Amount,Trxn_Date,Account_Id) Values (6,10,'02-APR-2015',2);
 Insert Into Transactions(Id,Amount,Trxn_Date,Account_Id) Values (7,10,'02-JUN-2015',2);
 Insert Into Transactions(Id,Amount,Trxn_Date,Account_Id) Values (8,10,'02-AUG-2015',2);     

数据检查:

   Select Unique(Account_Id) From Accounts A
 Inner Join Owner B on B.ID=A.OWNER_ID 
 Inner Join Transactions I on I.ACCOUNT_ID=A.Id
   Where I.Trxn_date Between '01-FEB-2015' and '01-JUL-2015' 
 And A.Status='CLOSED'
 and A.Balance=5000;/*1 Row Returned*/

循环必须在第一个返回的 Id 处退出

   Declare
   l_NewDate date:='01-FEB-2015';
   l_OldDate date:='01-JUL-2015';
   l_pID number(10);

 Begin
   For I in (Select Account_Id From Transactions 
   Where Trxn_date Between l_NewDate and l_OldDate)

   Loop

   Select Id Into l_pID From 
   (Select B.Id From Accounts A 
   Inner Join Owner B on A.Owner_Id = B.Id
   Where A.Status = 'CLOSED' And A.Balance = 5000 And A.Id=I.Account_Id)
   Where rownum < 2;
   dbms_output.put_line(l_pID);
   Exit;

   End Loop;
   End;

 ORA-01403: No data found

 ORA-06512: at line 12

我不明白为什么上面的数据检查清楚地表明没有找到数据。

问候 J.奥尔森

【问题讨论】:

    标签: oracle oracle11g ora-06512 ora-01403


    【解决方案1】:

    就像你说的,你的数据检查查询:

    Select Unique(Account_Id)
      From Accounts A
     Inner Join Owner B on B.ID=A.OWNER_ID 
     Inner Join Transactions I on I.ACCOUNT_ID=A.Id
     Where I.Trxn_date Between '01-FEB-2015' and '01-JUL-2015' 
       And A.Status='CLOSED'
       and A.Balance=5000;
    

    ... 返回单个 Account_Id 值为 2 的单行。

    但是,您的 PL/SQL 代码基本上将逻辑拆分为 2 个查询。您循环的查询是:

    Select Account_Id
      From Transactions 
     Where Trxn_date Between '01-FEB-2015' and '01-JUL-2015'
    

    而且,当我运行它时,它会返回:

    5
    5
    5
    2
    2
    2
    

    现在不能保证上述顺序,因为您没有ORDER BY 子句。但是,如果您以与我相同的顺序获得结果,那么您的第一次循环迭代将使用5 作为输入执行下一个查询:

    Select *
      From Accounts A 
     Inner Join Owner B on A.Owner_Id = B.Id
     Where A.Status = 'CLOSED'
       And A.Balance = 5000
       And A.Id = 5
    

    ...它不返回任何数据,这就是你得到错误的原因。

    如果您有幸从2 的值开始:

    Select *
      From Accounts A 
     Inner Join Owner B on A.Owner_Id = B.Id
     Where A.Status = 'CLOSED'
       And A.Balance = 5000
       And A.Id = 2
    

    ...它会按预期工作。

    我希望我能推荐一个合适的解决方案,但我只是不真正理解你想要做什么。但确实感觉你不应该需要 PL/SQL 循环来做你想做的事。一个简单的查询就足够了。您的数据检查查询似乎是一个好的开始。

    编辑

    对于它的价值,我认为这是一种更直接的方式来做你打算做的完全相同的事情(没有循环):

    Declare
       l_NewDate date:='01-FEB-2015';
       l_OldDate date:='01-JUL-2015';
       l_pID number(10);
     Begin
       select o.id into l_pID
        from transactions t
        join accounts a
          on a.id = t.account_id
         and a.status = 'CLOSED'
         and a.balance = 5000
        join owner o
          on o.id = a.owner_id
       where t.trxn_date between l_NewDate and l_OldDate
         and rownum < 2;
    
      dbms_output.put_line(l_pID);
    End;
    

    【讨论】:

    • 感谢您的帮助。我想要实现的是提取第一个通过我的标准的可用帐户并将所有者 ID 选择到变量 l_pID 中。我在上面创建的表格实际上是对我的实际数据的简化。实际上,事务表是具有数百万行的复杂表。同样适用于所有者和帐户表。问题有两点: 1. Transaction 表的全表访问很慢。 2. 账户不需要有交易。我可以使用“左外连接”,但这也很慢。
    • 解决方法很慢。选择 Unique(O.Id) from Accounts A Inner Join Owner O on O.Id=A.OWNER_ID Left external join Transactions T on T.ACCOUNT_ID=A.Id where A.Status = 'CLOSED' and A.Balance =5000 And trxn_date 介于 '01-FEB-2015' 和 '01-JUL-2015' 和 rownum
    猜你喜欢
    • 2014-02-06
    • 2014-03-28
    • 2022-01-19
    • 1970-01-01
    • 1970-01-01
    • 2013-11-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多