uso

雑記いろいろ
★書いてある内容に保証は一切ありません。
 ご自身で判断をしてください。

[DB] Oracle関数

2010-04-28 18:14:50 | work
Oracleの関数類

■ 文字列切り取り

 SUBSTR ( string , position [, length] )
 SUBSTRB ( string , position [, length] )

  string 対象の文字列
  position 正の場合 取り出したい文字列の開始位置(1~)
  position 0 の場合 1を指定したことと同じ
  position 負の場合 文字の末尾から逆向きに数えた位置
  length 取り出す文字列長(default 最後まで)
  
  参考:http://www.shift-the-oracle.com/sql/functions/substr.html
  
  
  
  
■ ビット演算
  
  BITAND ( number1 , number2 )
  return [ NUMBER ]
  
   number1 数値式 (NUMBER 型)
   number2 数値式 (NUMBER 型)
   
  数値式 number1 と number2 の論理積を NUMBER 型で戻す
  
 [使い方]
  数値式 number1 と number1 を バイナリデータとしてビットにし、
  その論理積(AND)処理を行い。その結果を数値として戻す。
  
  ※SQL 関数として BITAND 以外のビット演算は用意されていない。
   パッケージとしては UTL_RAW パッケージが利用できる。
  
  DECODE と BIN_TO_NUM 関数を併用して ON になっているビットの検出するなどの用途がある。
  → BITAND(bin_to_num(1,0,1), bin_to_num(0,0,1))
  
  bin_to_numはこの辺で確認
  http://www.shift-the-oracle.com/sql/functions/bin_to_num.html


■ 列項目を結合して一つの文字列として返す

  wmsys.wm_concat関数

  隠し関数、Oracle11gから使えるが、マニュアルには載っていないサポート外。
  なので、結局使わなかったが・・・。

  便利は便利。
  
  公式にはないので、この辺とか、
  Thttp://codezine.jp/article/detail/2690?p=2
  この辺でいろいろと書いてある
  http://www.drk7.jp/MT/archives/001395.html

  隠し関数は意外と多いらしい。

■ イラっとする挙動
  
  to_date(SYSDATE , 'yyyy/mm/dd hh24:mi:ss')

  答え : 2010/07/16

  あれ?
  
  SYSDATEはそのまま取ってくるとyyyy/mm/dd hh24:mi:ss形式になるらしい。
  まったく気がつかず、危うく問題になるとこだった。地味にイラっとする。。

  ちなみに、Oracleのバージョンによってはエラーになる。

  DATE型をto_dateにするとやはり変になる。SYSDATEが変になるのと似たような理由かな。
  DATE[14]のA(yyyy/mm/dd hh24:mi:ss)をyyyy/mm/dd形式でto_dateすると

  to_date(A,'yyyy/mm/dd')
  答え:0010/7/22

  to_charにするとちゃんと変換されるが、CHR型で返ってくる
  
  ふーん、と思いながら適当に使っていたら、後で痛い目にあった。

  たとえば、DATE[14]をyyyy/mm/ddで期間指定する場合。
  対象データが「2010/07/22 10:10:25」とかだったとすると、

  AAA between to_date('2010/07/20' , 'yyyy/mm/dd') and ('2010/07/25' , 'yyyy/mm/dd')
  だったら、別に問題なく、対象データが検索される。
  しかし、

  AAA between to_date('2010/07/22' , 'yyyy/mm/dd') and ('2010/07/22' , 'yyyy/mm/dd')
  だと、「2010/07/22 10:10:25」は引っかからない。
  これは、to_date('2010/07/22' , 'yyyy/mm/dd')=2010/07/22 00:00:00だから。
  2010/07/22 00:00:00~2010/07/22 00:00:00では、「2010/07/22 10:10:25」は引っかからない。
  
  対処方法
  深く考えず、適当にやっていたので、対処がバラバラだったと思う。
  ①末尾に00:00:00~23:59:59を付ける
  ②to_char(AAA , 'yyyy/mm/dd')で強制的に変換して、文字列検索する
  
  ②は気分的に嫌だったのでやらなかったような気がする・・・
  文字列比較すると大小関係がちゃんと検索されるのかなぁ・・・なんてことを考えて。