hashdata与Oracle,与Oracle语法上的差异

与Oracle语法上的差异

在这一章节中,我们简单比较一下,HashData 在语法层面与 Oracle 的差异。

数据类型

字符类型

Oracle

HashData

备注

char(n)

char(n)

字节为单位,定长,不足用空格填充

nchar(n)

char(n)

字符为单位,定长,不足用空格填充

varchar2(n)

varchar(n)

字节为单位,变长,有长度限制

nvarchar2(n)

varchar(n)

字符为单位,变长,有长度限制

string

text

字符为单位,变长,没有长度限制

一般情况下,对于 Oracle 的 char 和 nchar 类型,直接换成 HashData 的 char 是没有问题的;而对于变长的 varchar2 和 nvarchar2,想图省事的话,直接换成 HashData 的 TEXT 就可以。

数值类型

Oracle

HashData

备注

SMALLINT

SMALLINT

2个字节

INTEGER

INTEGER

4个字节

BIGINT

BIGINT

8个字节

BINARY_FLOAT

DOUBLE PRECISION

8个字节,15位精度

BINARY_DOUBLE

DOUBLE PRECISION

8个字节,15位精度

FLOAT

DOUBLE PRECISION

8个字节,15位精度

DOUBLE PRECISION

DOUBLE PRECISION

8个字节,15位精度

REAL

REAL

4个字节,6位精度

DECIMAL

DECIMAL

没有精度限制

NUMBER

NUMERIC

没有精度限制

Oracle 的数值类型向 HashData 的数值类型迁移过程中,只要根据 Oracle 数据的精度,在 HashData 中选择相同或者更大精度的类型,数据就能够顺利地迁移过来。但是为了转换过来后数据库的效率(特别是整数类型的时候),需要选择合适的数据类型,才能够完整、正确并且高效地完成 Oracle 数据类型向 HashData 数据类型的迁移。

时间类型

Oracle

HashData

备注

Date

Timestamp(0) without time zone

包含年,月,日,时,分和秒6个字段

Date

只包含年,月和日3个字段

Timestamp

Timestamp without time zone

包含年,月,日,时,分,秒和毫秒

Timestamp with time zone

Timestamp with time zone

带时区的时间戳

Timestamp with local time zone

Timestamp with time zone

带时区的时间戳

Interval

Interval

时间间隔

Oracle 的日期时间类型向 HashData 的数据迁移相对来说简单一些。由于 HashData 的数据类型的极值超越 Oracle,因此,数据迁移过程中,只要根据 Oracle 的数据精度,在 HashData 中选择正确的数据类型,并留意一下二者写法的不同,应该就能够完整正确地迁移过来。

大对象

Oracle

HashData

备注

BLOB

BYTEA

字节

CLOB

TEXT

字符

其他类型

Oracle

HashData

备注

RAW

BYTEA

RAWID

OID

常用函数

字符串操作函数

Oracle

HashData

备注

\

\

\

\

字符串连接符

concat

\

\

字符串连接函数

to_number

to_number

将字符串转换成数值

to_char

::TEXT

类型转换

to_date

to_timestamp

将字符串转化为时间戳

last_date

(date_trun('MONTH', mydate) + INTERVAL '1 MONTH' - INTERVAL '1 DAY')::DATE

当月的最后一天

instr

position

在一个字符串中,查找另外一个字符串出现的位置

substr

substr

截取字符串的一部分

length

length

获取字符串的长度

trim

trim

出去字符串开始和结束的指定字符

initcap

initcap

首字母大写

upper

upper

转大写

lower

lower

转小写

regexp_replace

regexp_replace

正则表达式替换

regexp_substr

substring

根据正则表达式寻找子串

regexp_instr

position(substring)

在一个字符串中查找符合正则表达式的字符串的位置

regexp_like

length(substring)

判断是否有满足条件的子串

数值函数

Oracle

HashData

备注

BITAND

&

对数值按位进行 与 运算

REMAINDER

%

取模

abs

abs

取绝对值

日期函数

Oracle

HashData

备注

SYSDATE

CURRENT_DATE

当前日期

CURRENT_TIMESTAMP

CURRENT_TIMESTAMP/NOW()

当前时间戳

ADD_MONTHS

DATE + INTERVAL

将日期往期推

EXTRACT

EXTRACT

从日期和时间戳中取出年,月,日等

其他函数

decode 是 Oracle 固有的一个函数,用于条件判断。其格式为:

decode(条件,值1,返回值1,值2,返回值2,...,值n,返回值n,缺省值)

当条件等于值 1 的时候返回返回值 1,等于值 n 的时候返回返回值 n,都不等于的时候返回缺省值。

在 HashData 中,decode 函数是用来解码的,和 encode 函数相对。对于 Oracle 的 decode 函数,可以把它转换成 case when 的 SQL 语句,得到一样的效果。另外,Oracle 也支持 case when 的语法,用法和 HashData 一样。

-- Oracle

select decode(y.studentcode, null, '0', '1') studenttype from y;

-- HashData

select case when y.studentcode is null then '0' else '1' end studenttype from y;

存储过程

最简单的存储过程

Oracle

CREATE OR REPLACE PROCEDURE procedure_name

AS

BEGIN

-- comments

NULL;

END;

HashData

CREATE OR REPLACE FUNCTION function_name() RETURNS VOID AS

$$

BEGIN

-- comments

NULL;

END;

$$ LANGUAGE PLPGSQL;

带输入输出参数的存储过程

Oracle

CREATE OR REPLACE PROCEDURE sum_n_product(x IN INTEGER, y IN INTEGER, sum OUT INTEGER, prod OUT INTEGER)

AS

BEGIN

sum := x + y;

prod := x * y;

END;

HashData

CREATE OR REPLACE FUNCTION sum_n_product(x INTEGER, y INTEGER, OUT sum INTEGER, OUT prod INTEGER) AS

$$

BEGIN

sum := x + y;

prod := x * y;

END;

$$ LANGUAGE PLPGSQL;

SELECT INTO

Oracle

CREATE OR REPLACE PROCEDURE find_record(key IN INTEGER, value OUT INTEGER)

AS

BEGIN

SELECT val INTO value FROM mytable WHERE id = key;

END;

HashData

CREATE OR REPLACE FUNCTION find_record(key INTEGER, OUT value INTEGER) AS

$$

BEGIN

SELECT val INTO value FROM mytable WHERE id = key;

END;

$$ LANGUAGE PLPGSQL;

带条件判断的存储过程

Oracle

CREATE OR REPLACE PROCEDURE fib(num IN INTEGER, result OUT INTEGER)

AS

BEGIN

IF NUM <= 0 THEN

result := 0;

ELSEIF num = 1 THEN

result := 1;

ELSE

result := fib (num - 1) + fib (num - 2);

END IF;

END;

HashData

CREATE OR REPLACE FUNCTION fib(INTEGER) RETURNS INTEGER AS

$$

DECLARE

result INTEGER := 0;

num ALIAS FOR $1;

BEGIN

IF num = 1 THEN

result := 1;

ELSEIF num > 1 THEN

result := fib(num - 1) + fib(num - 2);

END IF;

RETURN result;

END;

$$ LANGUAGE PLPGSQL;

动态执行

Oracle 和 HashData 基本是一样的:

EXECUTE 'DELETE FROM mytable WHERE id = key';

执行没有返回值的查询

Oracle 和 HashData 基本也是一样的:

UPDATE mytable SET val = val + delta WHERE id = key;

INSERT INTO mytable VALUES(key, value);

TRUNCATE TABLE mytable;

DELETE FROM mytable WHERE id = key;

LOOP循环

简单的 LOOP 循环

EXIT

LOOP

-- some computations

IF count > 0 THEN

EXIT; -- exit loop

END IF;

END LOOP;

LOOP

-- some computations

EXIT WHEN count > 0; -- same result as previous example

END LOOP;

BEGIN

-- some computations

IF stocks > 10000 THEN

EXIT; -- cause exit from the BEGIN block

END IF;

END;

CONTINUE

LOOP

-- some computations

EXIT WHEN count > 100;

CONTINUE WHEN count < 50;

-- some computations for count IN [50 ... 100] END LOOP;

WHILE

WHILE amount_owed > 0 AND gift_certificate_balance > 0 LOOP

-- some computations here

END LOOP;

WHILE NOT boolean_expression LOOP

-- some computations here

END LOOP;

FOR (integer variant)

FOR i IN 1..10 LOOP

-- some computations here

RAISE NOTICE 'i is %', i;

END LOOP;

FOR i IN REVERSE 10..1 LOOP

-- some computations here

END LOOP;

FOR i IN REVERSE 10..1 BY 2 LOOP

-- some computations here

RAISE NOTICE 'i is %', i;

END LOOP;

返回结果集的 LOOP

CREATE OR REPLACE FUNCTION cs_refresh_mviews() RETURNS INTEGER AS $$

DECLARE

mviews RECORD;

BEGIN

FOR mviews IN SELECT * FROM cs_materialized_views ORDER BY sort_key LOOP

EXECUTE 'TRUNCATE TABLE ' || quote_ident(mviews.mv_name);

EXECUTE 'INSERT INTO ' || quote_ident(mviews.mv_name) || ' ' || mviews.mv_query;

END LOOP;

RETURN 1;

END;

$$ LANGUAGE PLPGSQL;

游标

在 HashData 中,我们一般很少使用游标,因为当我们使用 FOR LOOP 的时候,数据库后台自动就会转化成游标。不过,这里我们还是可以简单介绍一下HashData 中游标的使用。

游标的声明

DECLARE

curs1 refcursor;

curs2 CURSOR FOR SELECT * FROM tenk1;

curs3 CURSOR (key INTEGER) IS SELECT * FROM tenk1 WHERE unique1 = key;

第一个游标 curs1 是一个通用游标,没有绑定具体的查询;第二个游标 curs2 绑定了具体的查询;第三个游标 curs3 也是一个绑定游标,而且是一个带参数的游标。

打开没有绑定查询的游标

普通查询

OPEN curs1 FOR SELECT * FROM foo WHERE key = mykey;

动态查询

OPEN curs1 FOR EXECUTE 'SELECT * FROM ' || quote_ident($1);

打开已经绑定查询的游标

OPEN curs2;

OPEN curs3(42);

使用游标

FETCH curs1 INTO rowvar;

FETCH curs2 INTO foo, bar, baz;

关闭游标

CLOSE curs1;

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值