【问题标题】:Assign value to array from plsql block从 plsql 块为数组赋值
【发布时间】:2015-04-23 08:35:53
【问题描述】:

我在 Oracle Forms 详细信息块中有以下代码

BEGIN
v_product_no := :detail_block.product_no;
Go_block('detail_block');
first_record;
--some if condition
WHILE :SYSTEM.last_record != 'TRUE' LOOP        
next_record;     
if(:detail_block.product_no = v_product_no) then  
 -- other condtions

end if;

END LOOP;

我想将v_product_no 存储到某种集合对象中,以便与:detail_block.product_no 的值进行比较。

我该怎么做?

编辑 1

product_no 将具有 K1BATTERYK2BATTERYZCATBATEERY 等值。 因此,如果K1BATTERY:detail_block.product_no 相同,则继续下一个条件

编辑 2

Go_block('detail_block');
v_product_no := :detail_block.product_no;
v_products(v_product_no) := 1;

first_record;

WHILE :SYSTEM.last_record != 'TRUE' LOOP            

    if(v_products.exists(v_product_no)) then
        alert('duplicate');  
            end if;     
    END LOOP;

END if;   

编辑 3

Go_block('detail_block');
v_product_no := :detail_block.product_no;
v_products(v_product_no) := 1;

    first_record;

    -- condition 


    WHILE :SYSTEM.last_record = 'FALSE' LOOP    
        next_record;        
        v_product_no := :detail_block.product_no;
        if(v_products.exists(v_product_no)) then
            alert('duplicate'); 
             else
      v_products(v_product_no) := 1; 

            end if;

        END LOOP;

    END if;

【问题讨论】:

  • 你真的需要一个集合对象吗?如果它是标量值,您可以创建一个包规范并让它存储该值。另外,为什么不将其存储到本地块变量中?
  • @Sathya 我的意图是如果product_no 被重复,那么我希望在同一个细节块中评估另一个 if 条件。将v_product_no 存储在varchar2 中无助于比较多记录块中的值。谢谢
  • 您不需要集合类型来存储标量值。在本地声明另一个变量并赋值,它可以在会话范围内使用,因为它是一个局部变量。
  • @LalitKumarB 如果我声明为局部变量,如何将多记录块中的所有项目与当前记录的项目值进行比较?
  • 也许不清楚。 :detail_block.product_no 分配了什么样的值?请举个例子,我会尽力重现你想要的。

标签: oracle plsql oracleforms


【解决方案1】:

使用 pl/sql 关联数组存储已处理的值。

declare
  type t_processed is table of number(1) index by varchar2(100);
  v_product_no varchar2(100); --hold the current value
  v_products t_processed;     --hold all processed values as keys
begin
  v_product_no := :detail_block.product_no;
  v_products(v_product_no) := 1; --create entry (v_product_no, 1)
  ...
  --later in while
  v_product_no := :detail_block.product_no;
  if(v_products.exists(v_product_no)) then --entry exists
  -- other conditions
  else
      v_products(v_product_no) := 1; --create entry (v_product_no, 1)
  end if;
...

【讨论】:

  • 我试过这个,但是它在while循环中检查存在条件,它进入了一个无限循环。
  • @Polppan 这是你的循环中的一个问题,而不是这个一般结构中的问题
  • 我已将我的代码 sn-p 作为编辑 2 包含在我的问题中
  • 是的,它确实需要用户操作。
  • 我有没有 prod_no 重复条目的情况,但它仍然显示重复记录作为警报。我已将代码 sn-p 包含在 Edit 3 中。
【解决方案2】:

我认为您在 v_product_no 变量中有Varying IN list of values

你可以通过以下方式进行,

测试#1

SQL> var product_no VARCHAR2(1000)
SQL> exec :product_no := 'K1BATTERY'

PL/SQL procedure successfully completed.

SQL>
SQL> SET SERVEROUTPUT ON
SQL>
SQL> DECLARE
  2    v_product_no VARCHAR2(1000);
  3  BEGIN
  4    v_product_no := 'K1BATTERY, K2BATTERY, ZCATBATEERY';
  5    IF :product_no IN (trim(regexp_substr(v_product_no, '[^,]+'))) THEN
  6      DBMS_OUTPUT.PUT_LINE('FOUND A MATCH');
  7    ELSE
  8      DBMS_OUTPUT.PUT_LINE('NO MATCH FOUND');
  9    END IF;
 10  END;
 11  /
FOUND A MATCH

PL/SQL procedure successfully completed.

测试#2

SQL> var product_no VARCHAR2(1000)
SQL> exec :product_no := 'ABCD'

PL/SQL procedure successfully completed.

SQL>
SQL> SET SERVEROUTPUT ON
SQL>
SQL> DECLARE
  2    v_product_no VARCHAR2(1000);
  3  BEGIN
  4    v_product_no := 'K1BATTERY, K2BATTERY, ZCATBATEERY';
  5    IF :product_no IN (trim(regexp_substr(v_product_no, '[^,]+'))) THEN
  6      DBMS_OUTPUT.PUT_LINE('FOUND A MATCH');
  7    ELSE
  8      DBMS_OUTPUT.PUT_LINE('NO MATCH FOUND');
  9    END IF;
 10  END;
 11  /
NO MATCH FOUND

PL/SQL procedure successfully completed.

SQL>

【讨论】:

  • 这是一个风险,因为您不知道记录的数量,并且您可能会用完可变大小
猜你喜欢
  • 2023-01-27
  • 1970-01-01
  • 2014-12-17
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-12-17
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多