4.16.4 使用例
表T1のC1=1である行の列C2データを,あるバイナリデータ列(search_data)から始まる400キロバイトの部分だけ,別のデータ(change_data)に置き換えます。それをC2列とした新しい行(C1=2)として,表T1に挿入します。
表T1の各列のデータ型を次に示します。
-
C1:INTEGER NOT NULL (INDEX)
-
C2:BLOB (100M) NOT NULL
void abnormalend(void);
main()
{
EXEC SQL BEGIN DECLARE SECTION;
SQL TYPE IS BLOB AS LOCATOR alldata_loc; /* 全データを表す位置付け子 */
long change_pos; /* 変更開始位置 */
SQL TYPE IS BLOB(10) search_data; /* 検索バイナリデータ列 */
SQL TYPE IS BLOB(400K) change_data; /* 変更バイナリデータ列 */
SQL TYPE IS BLOB AS LOCATOR enddata_loc; /* 変更部分の後に続く */
/* データを表す位置付け子 */
long pos;
EXEC SQL END DECLARE SECTION;
-------(HiRDBへのCONNECT処理(省略)) -------
-------(検索バイナリデータ列の設定(省略))-------
-------(変更バイナリデータ列の設定(省略))-------
EXEC SQL WHENEVER SQLERROR PERFORM abnormalend;
/* 列データを位置付け子で取得 */
EXEC SQL SELECT C2 INTO :alldata_loc FROM T1 WHERE C1 = 1;
/* 検索バイナリデータ列を含む開始位置を取得 */
EXEC SQL SET :change_pos = POSITION(:search_data AS BLOB(10)
IN :alldata_loc AS BLOB(100M));
pos = change_pos + 409600;
/* 変更部分の後に続くデータを位置付け子で取得 */
EXEC SQL SET :enddata_loc = SUBSTR(:alldata_loc AS BLOB(100M), :pos);
pos = change_pos -1;
/* 変更部分より前のデータを位置付け子を用いてINSERT */
EXEC SQL INSERT INTO T1 VALUES(2, SUBSTR
(:alldata_loc AS BLOB(100M), 1, :pos));
/* 全データを表す位置付け子は必要なくなったので無効化する */
EXEC SQL FREE LOCATOR :alldata_loc;
/* 変更部分のデータを連結してUPDATE */
EXEC SQL UPDATE T1 SET C2 = C2 || :change_data WHERE C1 = 2;
/* 変更部分の後に続くデータを位置付け子を用いて連結してUPDATE */
EXEC SQL UPDATE T1 SET C2 = C2 || :enddata_loc WHERE C1 = 2;
EXEC SQL COMMIT;
printf(" *** normally ended ***\n");
EXEC SQL WHENEVER SQLERROR CONTINUE;
EXEC SQL WHENEVER SQLWARNING CONTINUE;
EXEC SQL DISCONNECT;
return(0);
}
void abnormalend()
{
int wsqlcode;
wsqlcode = -SQLCODE;printf("\n*** HiRDB SQL ERROR SQLCODE
= %d \n", wsqlcode);
printf("SQLERRMC = %s\n", SQLERRMC);
EXEC SQL ROLLBACK;
EXEC SQL DISCONNECT;
exit(1);
}