How can i execute code faster by using PLSQL - oracle

----- My code is taking so much time to execute .it takes 1074 seconds to execute. Can someone tell me any way so that I can execute more faster--------
set serveroutput on;
declare
table_or_view_does_not_exist exception;
pragma exception_init(table_or_view_does_not_exist,-00942);
d_table varchar2(200);
q_table varchar2(200);
r_emp SYS.ODCINUMBERLIST := SYS.ODCINUMBERLIST();
type t_list is table of all_tab_columns%rowtype index by PLS_INTEGER;
v_array t_list;
begin
begin
d_table:='drop table subs_profile_spcl_char PURGE';
execute immediate d_table;
exception
when table_or_view_does_not_exist then
null;
end;
dbms_output.put_line('Table has been dropped');
q_table:='create table subs_profile_spcl_char
(column_name varchar2(50),
spcl_char_count Number)';
execute immediate q_table;
dbms_output.put_line('Table has been created');
dbms_output.enable;
select /*parallel(14)*/ * bulk collect into v_array from all_tab_columns where table_name='SUBSCRIBER_PROFILE' and OWNER='MIG';
for i in 1..v_array.count() loop
r_emp.extend;
EXECUTE IMMEDIATE
'select /*parallel(16)*/ count(*) from '||v_array(i).table_name||' where not regexp_like ('||v_array(i).column_name||',''[A-za-z0-9.]'')'
into r_emp(i);
if r_emp(i)<>0 then
dbms_output.put_line(v_array(i).column_name||'------------>>>>'||r_emp(i));
execute immediate 'insert into subs_profile_spcl_char values (:param1,:param2)' using v_array(i).column_name,r_emp(i);
end if;
end loop;
end;

The way I see it, a few objections.
you shouldn't drop/create table within PL/SQL; that's just bad practice. Create table at SQL level, then remove its contents (if you have to) in a procedure (truncate is faster than delete, but is irreversible. As you actually dropped the table, I'd say that you can use it)
target table is wrongly created anyway; knowing only the column name is far from enough - you should be storing owner and table name as well
it seems that you're looking for columns that contain "special characters" (i.e. not alphanumerics nor dots); in that case, modify regular expression
no need to scan all owners - SYS, SYSTEM, CTXSYS, possible APEX_ users most probably aren't interesting in what you're doing so - remove them. Remove other owners as well, if you want.
no need to scan all columns - numbers and dates can't contain special characters - filter only CHAR datatype family columns
no need to use r_emp collection. Fetch the count into a scalar variable (l_cnt in my example)
parallel "hint" is wrongly used. The way you put it, it is just a comment, not a hint. Hint looks like e.g. select /*+ parallel */ (you're missing a plus sign)
dbms_output takes resources; remove it if you don't need it (you don't; the result is anyway stored into the table)
insert into the target table doesn't require dynamic SQL so - switch to an ordinary insert
OK, here you go, here's what you might try to do.
(re)create the target table at SQL level:
SQL> DROP TABLE subs_profile_spcl_char;
Table dropped.
SQL> CREATE TABLE subs_profile_spcl_char
2 (
3 owner VARCHAR2 (30),
4 table_name VARCHAR2 (30),
5 column_name VARCHAR2 (30),
6 spcl_char_count NUMBER
7 );
Table created.
PL/SQL code:
SQL> set timing on
SQL>
SQL> DECLARE
2 TYPE t_list_rec IS RECORD
3 (
4 owner all_tab_columns.owner%TYPE,
5 table_name all_tab_columns.table_name%TYPE,
6 column_name all_tab_columns.column_name%TYPE
7 );
8
9 TYPE t_list IS TABLE OF t_list_rec;
10
11 v_array t_list;
12 --
13 l_cnt NUMBER;
14 BEGIN
15 EXECUTE IMMEDIATE 'truncate table subs_profile_spcl_char';
16
17 SELECT owner, table_name, column_name
18 BULK COLLECT INTO v_array
19 FROM all_tab_columns
20 WHERE owner NOT LIKE '%SYS%'
21 AND owner NOT LIKE 'APEX%'
22 AND data_type LIKE '%CHAR%';
23
24 FOR i IN 1 .. v_array.COUNT ()
25 LOOP
26 BEGIN
27 EXECUTE IMMEDIATE 'select count(*) from '
28 || v_array (i).owner
29 || '.'
30 || v_array (i).table_name
31 || ' where not regexp_like ('
32 || v_array (i).column_name
33 || ',''^[A-za-z0-9.]+$'')'
34 INTO l_cnt;
35 EXCEPTION
36 WHEN OTHERS
37 THEN
38 -- for tables you can't access
39 NULL;
40 END;
41
42 IF l_cnt > 0
43 THEN
44 INSERT INTO subs_profile_spcl_char
45 VALUES (v_array (i).owner,
46 v_array (i).table_name,
47 v_array (i).column_name,
48 l_cnt);
49 END IF;
50 END LOOP;
51 END;
52 /
PL/SQL procedure successfully completed.
Elapsed: 00:00:00.58
SQL> set timing off
It took 580 miliseconds (as opposed to your 1000 seconds).
Number of scanned columns:
SQL> SELECT COUNT (*)
2 FROM all_tab_columns
3 WHERE owner NOT LIKE '%SYS%'
4 AND owner NOT LIKE 'APEX%'
5 AND data_type LIKE '%CHAR%';
COUNT(*)
----------
172
Without filter:
SQL> SELECT COUNT (*)
2 FROM all_tab_columns;
COUNT(*)
----------
39697
SQL>
Why would you check 40.000 columns, if you can do that on 200 columns instead?
Final result:
SQL> SELECT *
2 FROM subs_profile_spcl_char
3 ORDER BY owner DESC, table_name, column_name;
OWNER TABLE_NAME COLUMN_NAME SPCL_CHAR_COUNT
-------------------- ------------------------- -------------------- ---------------
XDB PATH_VIEW PATH 137
XDB RESOURCE_VIEW ANY_PATH 137
SCOTT BONUS JOB 1
SCOTT DEPT LOC 1
SCOTT PRODUCTS PRODUCT_NAME 4
SCOTT SUBS_PROFILE_SPCL_CHAR COLUMN_NAME 18
SCOTT SUBS_PROFILE_SPCL_CHAR OWNER 2
SCOTT SUBS_PROFILE_SPCL_CHAR TABLE_NAME 24
ORDS_METADATA USER_ORDS_OBJECTS OBJECT_ALIAS 3
ORDS_METADATA USER_ORDS_OBJECTS PARSING_OBJECT 3
ORDDATA ORDDCM_DBRELEASE_DOCS DOC_TYPE 3
ORDDATA ORDDCM_DOCUMENT_TYPES DOC_TYPE 4
<snip>
29 rows selected.
SQL>

Related

Exchange/Move a Oracle partition without interim table

I would like to exchange the Oracle partition to another partitioned table. But to do that we are using interim non partitioned table. Can this be done in a different way?
Can't we exchange a partition from one partitioned table to another without using non-partitioned table as a medium? Can't we directly move a partition to target table?
Easy to put a little API together to make this simple. In this example, T1 and T2 are matching, but T1 and T3 are not
SQL>
SQL> create table t1
2 partition by list ( owner) automatic
3 ( partition px values ('SYS') )
4 as select * from dba_objects;
Table created.
SQL>
SQL> create table t2
2 partition by list ( owner) automatic
3 ( partition py values ('SYS') )
4 as select * from dba_objects;
Table created.
SQL>
SQL> create table t3
2 partition by list ( owner) automatic
3 ( partition pz values ('SYSTEM') )
4 as select * from dba_segments;
Table created.
SQL>
SQL> create sequence seq;
Sequence created.
SQL>
SQL> create or replace
2 procedure exchange_par(
3 p_table1 varchar2,
4 p_table2 varchar2,
5 p_table1_par varchar2,
6 p_table2_par varchar2) is
7 l_tab_cnt int;
8 l_hash_cnt int;
9 l_interim varchar2(100);
10 begin
11 select count(distinct tot), count(*)
12 into l_hash_cnt, l_tab_cnt
13 from
14 ( select table_name, sum(ora_hash(column_name)) tot
15 from user_tab_cols
16 where table_name in (p_table1,p_table2)
17 group by table_name
18 );
19
20 if l_tab_cnt != 2 or l_hash_cnt != 1 then
21 raise_application_error(-20000,'Dead in the water');
22 end if;
23 l_interim := 'TMPTAB$'||seq.nextval;
24
25 begin
26 execute immediate
27 'drop table '||l_interim||' purge';
28 exception
29 when others then
30 if sqlcode = -942 then null; else raise; end if;
31 end;
32
33 execute immediate
34 'create table '||l_interim||' for exchange with table '||p_table1;
35
36 execute immediate
37 'alter table '||p_table1||' exchange partition '||p_table1_par||
38 ' with table '||l_interim;
39
40 execute immediate
41 'alter table '||p_table2||' exchange partition '||p_table2_par||
42 ' with table '||l_interim;
43
44 execute immediate
45 'drop table '||l_interim||' purge';
46
47 end;
48 /
Procedure created.
SQL>
SQL> exec exchange_par('T1','T2','PX','PY');
PL/SQL procedure successfully completed.
SQL>
SQL> exec exchange_par('T1','T3','PX','PZ');
BEGIN exchange_par('T1','T3','PX','PZ'); END;
*
ERROR at line 1:
ORA-20000: Dead in the water
ORA-06512: at "MCDONAC.EXCHANGE_PAR", line 20
ORA-06512: at line 1
SQL>
SQL>
SQL>
SQL>
Can make this as robust as you like with more conditions etc.

Oracle renaming auto generated list paritions

I have several environments where automatic list partitioning is implemented.
Some product managers don't like the system GENERATED partition name, which is being GENERATED and want to reference the partition by a more meaningful name.
In an effort to address those concerns I'm trying to create a procedure, which will rename the partition based on the high_value. In the example below I am partitioning by state so the names I want to generate are P_OHIO, P_IOWA..
In the procedure below I am getting the following error:
ORA-14048: a partition maintenance operation may not be combined with other operations ORA-06512:
Can someone please advise me on why I am getting this error and how to rectify it.
Thanks in advance for your help and expertise.
CREATE TABLE T21
(
seq_num NUMBER GENERATED BY DEFAULT AS IDENTITY (START WITH 1) NOT NULL,
num NUMBER(*,0),
state VARCHAR2(20)
)
SEGMENT CREATION DEFERRED
PARTITION BY LIST (state) AUTOMATIC
(PARTITION P_CALIFORNIA VALUES ('CALIFORNIA')
);
insert into t21 (num, state)
select
level * round(dbms_random.value(1,50)),
case round(dbms_random.value(1,50))
when 1 then 'Alabama'
when 2 then 'Alaska'
when 3 then 'Arizona'
when 4 then 'Arkansas'
when 5 then 'California'
when 6 then 'Colorado'
when 7 then 'Connecticut'
when 8 then 'Delaware'
when 9 then 'Florida'
when 10 then 'Georgia'
when 11 then 'Hawaii'
when 12 then 'Idaho'
when 13 then 'Illinois'
when 14 then 'Indiana'
when 15 then 'Iowa'
when 16 then 'Kansas'
when 17 then 'Kentucky'
when 18 then 'Louisiana'
when 19 then 'Maine'
when 20 then 'Maryland'
when 21 then 'Massachusetts'
when 22 then 'Michigan'
when 23 then 'Minnesota'
when 24 then 'Mississippi'
when 25 then 'Missouri'
when 26 then 'Montana'
when 27 then 'Nebraska'
when 28 then 'Nevada'
when 29 then 'New Hampshire'
when 30 then 'New Jersey'
when 31 then 'New Mexico'
when 32 then 'New York'
when 33 then 'North Carolina'
when 34 then 'North Dakota'
when 35 then 'Ohio'
when 36 then 'Oklahoma'
when 37 then 'Oregon'
when 38 then 'Pennsylvania'
when 39 then 'Rhode Island'
when 40 then 'South Carolina'
when 41 then 'South Dakota'
when 42 then 'Tennessee'
when 43 then 'Texas'
when 44 then 'Utah'
when 45 then 'Vermont'
when 46 then 'Virginia'
when 47 then 'Washington'
when 48 then 'West Virginia'
when 49 then 'Wisconsin'
when 50 then 'Wyoming'
end
from dual
connect by level <= 100;
SELECT TABLE_NAME, PARTITION_NAME, HIGH_VALUE FROM USER_TAB_PARTITIONS WHERE TABLE_NAME ='T21';
CREATE OR REPLACE PROCEDURE RenameListPartitions
IS
CURSOR PartTables IS
SELECT TABLE_NAME
FROM USER_PART_TABLES
WHERE PARTITIONING_TYPE = 'LIST'
ORDER BY TABLE_NAME;
CURSOR TabParts(aTableName VARCHAR2) IS
SELECT PARTITION_NAME, HIGH_VALUE
FROM USER_TAB_PARTITIONS
WHERE regexp_like(partition_name,'^SYS_P[[:digit:]]{1,10}') AND
TABLE_NAME = aTableName AND
table_name not like 'BIN$%'
ORDER BY PARTITION_POSITION;
newPartName VARCHAR2(30);
BEGIN
FOR aTab IN PartTables LOOP
FOR aPart IN TabParts(aTab.TABLE_NAME) LOOP
execute immediate 'select ' || aPart.HIGH_VALUE || ' from dual' into newPartName;
IF newPartName <> aPart.PARTITION_NAME THEN
EXECUTE IMMEDIATE 'ALTER TABLE '||aTab.TABLE_NAME||' RENAME PARTITION '||aPart.PARTITION_NAME||' TO '||newPartName;
END IF;
END LOOP;
END LOOP;
END RenameListPartitions;
/
EXEC RenameListPartitions;
Some of your partition values have spaces - like 'New York' - so you need to quote the identifiers for the partitions:
EXECUTE IMMEDIATE 'ALTER TABLE '||aTab.TABLE_NAME
||' RENAME PARTITION '||aPart.PARTITION_NAME
||' TO "'||newPartName||'"';
db<>fiddle
Of course, that means you also need to quote them when you refer to them explicitly in the future; it might be better to, say, replace spaces with underscores and change to uppercase, so you get NEW_YORK:
EXECUTE IMMEDIATE 'ALTER TABLE '||aTab.TABLE_NAME
||' RENAME PARTITION '||aPart.PARTITION_NAME
||' TO '||upper(replace(newPartName,' ','_'));
db<>fiddle

Passing DataTable to Oracle Procedure

I want to pass DataTable to Oracle procedure which creates a Temporary table.
Even My procedure needs changes to accept datatable as parameter.
I want datatable in place of existing_table.
Below is the Procedure:
CREATE OR REPLACE procedure temptable
is
begin
EXECUTE IMMEDIATE'CREATE GLOBAL TEMPORARY TABLE TEMP_TABLE
ON COMMIT PRESERVE ROWS
AS
select * from existing_table';
End;
How do I work through this. Please help!
Here's an example of how you might do that:
SQL> create or replace procedure temptable (par_table_name in varchar2)
2 is
3 l_cnt number;
4 l_str varchar2(200);
5 begin
6 -- if TEMP_TABLE already exists, drop it
7 select count(*)
8 into l_cnt
9 from user_tables
10 where table_name = 'TEMP_TABLE';
11
12 if l_cnt > 0 then
13 execute immediate 'drop table temp_table';
14 end if;
15
16 -- create a new TEMP_TABLE
17 l_str := 'create global temporary table temp_table on commit preserve rows ' ||
18 'as select * from ' || par_table_name;
19 execute immediate (l_str);
20 end;
21 /
Procedure created.
SQL> exec temptable('dept');
PL/SQL procedure successfully completed.
SQL> select * from temp_table;
DEPTNO DNAME LOC
---------- -------------------- --------------------
10 ACCOUNTING NEW YORK
20 RESEARCH DALLAS
30 SALES CHICAGO
40 OPERATIONS BOSTON
SQL>
However, in Oracle, you don't really create/drop tables dynamically - you create them once and use them many times. For a global temporary table, you'd create it once and populate as necessary in different sessions.
There might be requirements as yours (i.e. to use the same table name for different data sources), so - if that's your case, see if the above code helps.

Check if both column and table exist and run queries based on the result

I am trying to run some SQL queries on Oracle database, but before running the query I need to check if both table and column exists. If table exists and column does not exist, then run another query:
if table `testtable` exists and if table has column `testcolumn`
Run a SQL which returns the result
else if table `testtable` exists but column `testcolumn` not present
Run a different sql which also returns the result
else
print some defined string
You can use:
DECLARE
nCount NUMBER;
BEGIN
SELECT COUNT(*)
INTO nCount
FROM USER_TAB_COLS
WHERE TABLE_NAME = 'TESTTABLE' AND
COLUMN_NAME = 'TESTCOLUMN';
IF nCount > 0 THEN
-- Run a SQL which returns the result
ELSE
SELECT COUNT(*)
FROM USER_TABLES
WHERE TABLE_NAME = 'TESTTABLE';
IF nCount > 0 THEN
Run a different sql which also returns the result
ELSE
print some defined string
END;
You'll have to add code to run whatever SQL you're trying to run, and to print whatever message you need.
Best of luck.
Here's one option - check contents of USER_TAB_COLUMNS and - depending on what you find - use refcursor in order to return the result.
SQL> create or replace function f_test
2 return sys_refcursor
3 is
4 l_cnt number;
5 cur_r sys_refcursor;
6 begin
7 -- 1st test - this one fails
8 select count(*)
9 into l_cnt
10 from user_tab_columns
11 where table_name = 'EMP'
12 and column_name = 'DOES_NOT_EXIST';
13
14 if l_cnt > 0 then
15 open cur_r for select ename, job, sal from emp;
16 end if;
17
18 -- 2nd test - this one is OK
19 select count(*)
20 into l_cnt
21 from user_tab_columns
22 where table_name = 'DEPT'
23 and column_name = 'DEPTNO';
24
25 if l_cnt > 0 then
26 open cur_r for select dname, loc from dept;
27 end if;
28
29 return cur_r;
30 end;
31 /
Function created.
SQL> select f_test from dual;
F_TEST
--------------------
CURSOR STATEMENT : 1
CURSOR STATEMENT : 1
DNAME LOC
-------------- -------------
ACCOUNTING NEW YORK
RESEARCH DALLAS
SALES CHICAGO
OPERATIONS BOSTON
SQL>
It has to be some kind of a dynamic code because you can't just write a static SELECT statement that selects non-existent columns as you'd get ORA-00904: "DOES_NOT_EXIST": invalid identifier error.

How do you create a table with random number of fields in Oracle using PL/SQL?

I need to create a Oracle tables with random number of columns for load testing. I just want to specify number of columns with type NUMBER, number of columns with type VARCHAR2 etc and the fields should be generated automatically. Also, I will be filling up the tables with random data for which I will be using dbms_random.
How can I achieve this?
"I just want to specify number of
columns with type NUMBER, number of
columns with type VARCHAR2 etc and the
fields should be generated
automatically."
The following procedure does just that. Note that it is rather basic; you might want to make it more sophisticated, for example by varying the length of the varchar2 columns:
SQL> create or replace procedure bld_table
2 ( p_tab_name in varchar2
3 , no_of_num_cols in pls_integer
4 , no_of_var_cols in pls_integer
5 , no_of_date_cols in pls_integer
6 )
7 as
8 begin
9 execute immediate 'create table '||p_tab_name||' ('
10 ||' pk_col number not null'
11 ||', constraint '||p_tab_name||'_pk primary key (pk_col) using index)';
12 << numcols >>
13 for i in 1..no_of_num_cols loop
14 execute immediate 'alter table '||p_tab_name||' add '
15 ||' col_n'||trim(to_char(i))||' number';
16 end loop numcols;
17 << varcols >>
18 for i in 1..no_of_var_cols loop
19 execute immediate 'alter table '||p_tab_name||' add '
20 ||' col_v'||trim(to_char(i))||' varchar2(30)';
21 end loop varcols;
22 << datcols >>
23 for i in 1..no_of_date_cols loop
24 execute immediate 'alter table '||p_tab_name||' add '
25 ||' col_d'||trim(to_char(i))||' date';
26 end loop datcols;
27 end bld_table;
28 /
Procedure created.
SQL>
Here it is in action:
SQL> exec bld_table ('T23', 2, 3, 0)
PL/SQL procedure successfully completed.
SQL> desc t23
Name Null? Type
----------------------------------------- -------- ----------------------------
PK_COL NOT NULL NUMBER
COL_N1 NUMBER
COL_N2 NUMBER
COL_V1 VARCHAR2(30 CHAR)
COL_V2 VARCHAR2(30 CHAR)
COL_V3 VARCHAR2(30 CHAR)
SQL>
We can also use dynamic SQL to populate the table with rows of random data.
SQL> create or replace procedure pop_table
2 ( p_tab_name in varchar2
3 , p_no_of_rows in pls_integer
4 )
5 as
6 stmt varchar2(32767);
7 begin
8 stmt := 'insert into '||p_tab_name
9 || ' select rownum ';
10 for r in ( select column_name
11 , data_type
12 , data_length
13 from user_tab_columns
14 where table_name = p_tab_name
15 and column_name != 'PK_COL' )
16 loop
17 case r.data_type
18 when 'VARCHAR2' then
19 stmt := stmt ||', dbms_random.string(''a'', '||r.data_length||')';
20 when 'NUMBER' then
21 stmt := stmt ||', dbms_random.value(0, 1000)';
22 when 'DATE' then
23 stmt := stmt ||', sysdate + dbms_random.value(-1000, 0)';
24 end case;
25 end loop;
26 stmt := stmt || ' from dual connect by level <= '||p_no_of_rows;
27 execute immediate stmt;
28 end pop_table;
29 /
Procedure created.
SQL>
Note that the primary key is populated with the ROWNUM so it will most likely fail if the table already contains rows.
SQL> exec pop_table('T23', 4)
PL/SQL procedure successfully completed.
SQL> select * from t23
2 /
PK_COL COL_N1 COL_N2 COL_V1 COL_V2 COL_V3
---------- ---------- ---------- ------------------------------ ----------------------------- ------------------------------
1 913.797432 934.265814 NUtxjLoRQMCTLNMPKVGbTZwJeYaqnXTkCcWu WFRSHjXdLfpgVYOjzrGrtUoX jIBSoYOhSdhRFeEeFlpAxoanPabvwK
2 346.879815 104.800387 NTkvIlKeJWybCTNEdvsqJOKyidNkjgngwRNN PPIOInbzInrsVTmFYcDvwygr RyKFoMoSiWTmjTqRBCqDxApIIrctPu
3 93.1220275 649.335267 NTUxzPRrKKfFncWaeuzuyWzapmzEGtAwpnjj jHILMWJlcMjnlboOQEIDFTBG JRozyOpWkfmrQJfbiiNaOnSXxIzuHk
4 806.709357 857.489387 ZwLLkyINrVeCkUpznVdTHTdHZnuFzfPJbxCB HnoaErdzIHXlddOPETzzkFQk dXWTTgDsIeasNHSPbAsDRIUEyPILDT
4 rows selected.
SQL>
Again, there are all sorts of ways to improve the sophistication of the data.
As an aside, using these sorts of data pools for load testing is not always a good idea. Performance problems are often caused by skews in the distribution of data values which you just aren't going to get with DBMS_RANDOM. This is particularly true of some date columns - e.g. START_DATE - which would tend to be clustered together in real life but the above procedure will not generate that pattern. Similarly maxing out the varchar2 columns will lead to tables which take up more storage than they wlll under real-life usage.
In short, randomly generated data is better than nothing but we need to understand its weaknesses.
Two approaches
1) Write code to generate text files containing the CREATE TABLE commands that you need to run and populate your tables, then execute these using SQL*Plus.
2) Use Dynamic SQL embedded inside PL/SQL -
PROCEDURE create_random_table
(pTableName IN VARCHAR2,
pNumberOfColumns IN INTEGER)
IS
PRAGMA AUTONOMOUS_TRANSACTION;
lCommand VARCHAR2(32000);
BEGIN
lCommand :=
'CREATE TABLE '||pTableName||'(';
FOR i IN 1..pNumberOfColumns LOOP
append your column definition here
END LOOP;
lCommand := lCommand||';';
--
EXECUTE IMMEDIATE lCommand;
END;
You could also use 'CREATE TABLE AS SELECT' to populate your table at the same time (see other answer).
This should give you a good starting point - there isn't anything in the system that will do what you want without writing code.
You may generate such table by yourself.
Create table with required datatypes:
Create Table RandomTable
AS
Select dbms_random.string('A', 1) CharField,
dbms_random.string('a', 20) VarCharField,
TRUNC(dbms_random.value(0, 35000)) IntField,
dbms_random.value(0, 35000) NumberField,
Level SequenceField,
sysdate + dbms_random.value(-3500, 3500) DateField
from dual connect by level < 1000
(You can change 1000 to required rows numbers, and add required data types)
After that you can create or populate tables with random data from RandomTable
Create Table TestTable1
AS
SELECT CharField as a, NumberField as b
from RandomTable
INSERT INTO TestTable2(DateFrom, Quantity)
SELECT DateField, IntField
from RandomTable
Where SequenceField <= 500

Resources