Detailed description of string segmentation into a set in El

Source: Internet
Author: User
First, two functions are constructed in two ways.
The code is as follows: Copy code
-- Use conventional plsql
Create or replace function f_str2list_pls
(
P_str varchar2,
P_separator varchar2 default ','
) Return my_tk_str_tab_type is
Rochelle IDX pls_integer: = 0;
L_str varchar2 (32767): = trim (p_str );
Rochelle MT varchar2 (100): = null;
Rochelle list my_tk_str_tab_type: = my_tk_str_tab_type ();
Begin
While l_str is not null loop
Rochelle IDX: = instr (l_str, p_separator );
If l_idx = 0 then
L_elmt: = l_str;
Rochelle str: = null;
Else
L_elmt: = substr (l_str, 1, l_idx-1 );
L_str: = substr (l_str, l_idx + 1 );
End if;
 
Rochelle list.extend;
L_list (l_list.last): = trim (l_elmt );
End loop;
Return l_list;
End;
/
-- Use single SQL
Create or replace function f_str2list_ SQL
(
P_str varchar2,
P_separator varchar2 default ','
) Return my_tk_str_tab_type is
Rochelle list my_tk_str_tab_type: = my_tk_str_tab_type ();
Begin
Select substr (a. str,
Instr (p_separator | a. str, p_separator, 1, rn ),
Instr (a. str | p_separator, p_separator, 1, rn )-
Instr (p_separator | a. str, p_separator, 1, rn) q
Bulk collect into l_list
From (select p_str as str from dual),
(Select rownum rn from dual connect by rownum <= length (p_str) B
Where instr (p_separator | a. str, p_separator, 1, rn)> 0;
Return l_list;
End;
/
 
 

Verify that the two methods perform the same function
 
----------------------------------------------------
The code is as follows: Copy code
-- Same result
Declare
Rochelle list my_tk_str_tab_type: = my_tk_str_tab_type ();
L_str varchar2 (1000): = 'a, B, c ';
Begin
Rochelle list: = f_str2list_pls (l_str ,',');
For I in 1 .. l_list.count loop
Dbms_output.put_line (l_list (I ));
End loop;
 
Dbms_output.put_line ('');
Rochelle list: = f_str2list_ SQL (l_str ,',');
For I in 1 .. l_list.count loop
Dbms_output.put_line (l_list (I ));
End loop;
End;
/
SQL> set serveroutput on
A
B
C
 
A
B
C
 
 
 
 
 
We know that in PL/SQL and SQL, the varchar2 type length limit is different. Are the two methods subject to the same restrictions? Verify
First test the PL/SQL version
 
-- A single letter is used as an element and a comma delimiter is required. The maximum length of an element is 32767 in 2. PL/SQL. When (32767/2 = 16383) elements are retrieved, the operation is successful.
----------------------------------------------------
The code is as follows: Copy code
-- Pls versions tring length limit
Declare
Rochelle list my_tk_str_tab_type: = my_tk_str_tab_type ();
L_str varchar2 (32767): = '';
Rochelle Max pls_integer: = 16383;
Begin
-- Construct string
For I in 1 .. l_max loop
L_str: = l_str | ',' | 'A ';
End loop;
Rochelle str: = substr (l_str, 2 );
Rochelle list: = f_str2list_pls (l_str ,',');
End;
/
PL/SQL procedure successfully completed
-- Add an element. When getting (16384) elements, it exceeds the limit of varchar2, so it cannot run. (An error is returned when the string is constructed. f_str2list_pls has not been called yet)
The code is as follows: Copy code
Declare
Rochelle list my_tk_str_tab_type: = my_tk_str_tab_type ();
L_str varchar2 (32767): = '';
Rochelle Max pls_integer: = 16384;
Begin
-- Construct string
For I in 1 .. l_max loop
L_str: = l_str | ',' | 'A ';
End loop;
Rochelle list: = f_str2list_pls (l_str ,',');
End;
/
ORA-06502: PL/SQL: numeric or value error: character string buffer too small
ORA-06512: at line 9
-- Modify the code and actually call this function. The result shows that the f_str2list_pls () internal error is too long.
Declare
Rochelle list my_tk_str_tab_type: = my_tk_str_tab_type ();
L_str varchar2 (32767): = '';
Rochelle Max pls_integer: = 16383;
Begin
-- Construct string
For I in 1 .. l_max loop
L_str: = l_str | ',' | 'A ';
End loop;
L_list: = f_str2list_pls (l_str | ', ',',');
End;
 
ORA-06502: PL/SQL: numeric or value error: character string buffer too small
ORA-06512: at "T2.F _ STR2LIST_PLS", line 7
ORA-06512: at line 12
 
 
 

The SQL version is tested below
 
The code is as follows: Copy code
-- Because the upper limit of varchar2 in SQL is 4000, 2000 elements are used. Everything works.
----------------------------------------------------
-- SQL versions tring length limit
Declare
Rochelle list my_tk_str_tab_type: = my_tk_str_tab_type ();
L_str varchar2 (32767): = '';
Rochelle Max pls_integer: = 2000;
Begin
-- Construct string
For I in 1 .. l_max loop
L_str: = l_str | ',' | 'A ';
End loop;
Rochelle str: = substr (l_str, 2 );
Rochelle list: = f_str2list_ SQL (l_str ,',');
End;
/
PL/SQL procedure successfully completed
-- Directly add to 2001 elements. An error is reported in f_str2list_ SQL (), indicating that the string is successfully input, but cannot be processed by the function.
The code is as follows: Copy code
Declare
Rochelle list my_tk_str_tab_type: = my_tk_str_tab_type ();
L_str varchar2 (32767): = '';
Rochelle Max pls_integer: = 2001;
Begin
-- Construct string
For I in 1 .. l_max loop
L_str: = l_str | ',' | 'A ';
End loop;
Rochelle str: = substr (l_str, 2 );
Rochelle list: = f_str2list_ SQL (l_str ,',');
End;
 
ORA-01460: unimplemented or unreasonable conversion requested
ORA-06512: at "T2.F _ STR2LIST_ SQL", line 8
ORA-06512: at line 13
Note: the description of the ORA-01460 is not clear, in fact this is varchar2 super long
 
 
 
 
 
Test and compare the performance of the two methods under different data volumes
 
The code is as follows: Copy code
----------------------------------------------------
-- Performance test
Declare
Rochelle list my_tk_str_tab_type: = my_tk_str_tab_type ();
L_str varchar2 (32767): = '';
Rochelle Max pls_integer: = 2000;
Begin
-- Construct string
For I in 1 .. l_max loop
L_str: = l_str | ',' | 'A ';
End loop;
Rochelle str: = substr (l_str, 2 );
-- Warm up before actually calculation
Rochelle list: = f_str2list_ SQL (l_str ,',');
Rochelle list: = f_str2list_pls (l_str ,',');
 
-- Begin calc and diff
My_rs.rs_start;
-- 1. pls version
Rochelle list: = f_str2list_pls (l_str ,',');
My_rs.rs_middle;
-- 2. SQL version
Rochelle list: = f_str2list_ SQL (l_str ,',');
My_rs.rs_stop ();
End;
/
 
 
 

We will test the number of elements 100,200,500,100 0, 2000 respectively. Perform 3-5 times in each case and then take the average value
Number of elements
PL/SQL running time (1/100 second)
SQL running time (1/100 second)
PCT
100
1
1
100%
200
1
1-2
50%-100%
500
1-2
2-3
30%-50%
1000
1
4
25%
2000
2
10
20%
Summary:
The SQL version is easy to write and can be used directly from the PL/SQL environment (single SQL for row and column conversion ).
The SQL version can only process strings with a length less than 4000, and can contain a maximum of 2000 elements. PL/SQL can process strings with a length less than 32767.
When the data volume is small, the performance of the two is equivalent. As the data volume increases, PL/SQL performance is superior.
 
 

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.