0% found this document useful (0 votes)
46 views

Programmers Guide

Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
46 views

Programmers Guide

Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 314

InterBase 5 Server

Programmer’s
Guide

InterBase
SOFTWARE CORPORATION
®

1800 Green Hills Road Scotts Valley, CA 95066 http://www.interbase.com


February 27, 1998 (D:\5.1\5PGuide\PGTitle.fm5)

InterBase Software Corp. and Borland International may have patents and/or pending patent applications
covering subject matter in this document. The furnishing of this document does not convey any license to these
patents.
Copyright 1998 InterBase Software Corporation. All rights reserved. All InterBase products are trademarks or
registered trademarks of InterBase Software Corporation. All Borland products are trademarks or registered
trademarks of Borland International, Inc. Other brand and product names are trademarks or registered
trademarks of their respective holders.
INT0050WW21003 5E3R0298
9899000102-9 8 7 6 5 4 3 2 1
D4
Table of Contents

List of Tables . . . . . . . . . . . . . . . . . . ix 8VLQJWUDQVDFWLRQQDPHV            


List of Figures . . . . . . . . . . . . . . . . . . xi 3UHSURFHVVLQJSURJUDPV              

Chapter 1 Using the Programmer’s Guide Chapter 3 Working with Databases


:KRVKRXOGXVHWKLVJXLGH              'HFODULQJDGDWDEDVH                
7RSLFVFRYHUHGLQWKLVJXLGH              'HFODULQJPXOWLSOHGDWDEDVHV          
6DPSOHGDWDEDVHDQGDSSOLFDWLRQV           8VLQJKDQGOHVIRUWDEOHQDPHV        
8VLQJKDQGOHVZLWKRSHUDWLRQV        
Chapter 2 Application Requirements 3UHSURFHVVLQJDQGUXQWLPHGDWDEDVHV     
5HTXLUHPHQWVIRUDOODSSOLFDWLRQV           8VLQJWKH&203,/(7,0(FODXVH     
3RUWLQJFRQVLGHUDWLRQVIRU64/          8VLQJWKH5817,0(FODXVH         
3RUWLQJFRQVLGHUDWLRQVIRU'64/         &RQWUROOLQJ6(7'$7$%$6(VFRSH      
'HFODULQJKRVWYDULDEOHV              6SHFLI\LQJDFRQQHFWLRQFKDUDFWHUVHW       
6HFWLRQGHFODUDWLRQV               2SHQLQJDGDWDEDVH                
8VLQJ%$6('21WRGHFODUHYDULDEOHV     8VLQJVLPSOH&211(&7VWDWHPHQWV     
+RVWODQJXDJHGDWDVWUXFWXUHV          8VLQJDGDWDEDVHKDQGOH           
'HFODULQJDQGLQLWLDOL]LQJGDWDEDVHV          8VLQJVWULQJVRUKRVWODQJXDJHYDULDEOHV   
8VLQJ6(7'$7$%$6(             8VLQJDKDUGFRGHGGDWDEDVHQDPHV     
8VLQJ&211(&7                $GGLWLRQDO&211(&7V\QWD[         
:RUNLQJZLWKDVLQJOHGDWDEDVH          $WWDFKLQJWRPXOWLSOHGDWDEDVHV         
64/VWDWHPHQWV                   +DQGOLQJ&211(&7HUURUV          
(UURUKDQGOLQJDQGUHFRYHU\            6HWWLQJGDWDEDVHFDFKHEXIIHUV         
&ORVLQJWUDQVDFWLRQV                 6HWWLQJLQGLYLGXDOGDWDEDVHEXIIHUV      
$FFHSWLQJFKDQJHV                6SHFLI\LQJEXIIHUVIRUDOOGDWDEDVHV     
8QGRLQJFKDQJHV                 $FFHVVLQJDQRSHQGDWDEDVH            
&ORVLQJGDWDEDVHV                  'LIIHUHQWLDWLQJWDEOHQDPHV            
'64/UHTXLUHPHQWV                 &ORVLQJDGDWDEDVH                 
'HFODULQJDQ;64/'$              :LWK',6&211(&7              
'64/OLPLWDWLRQV                  :LWK&200,7DQG52//%$&.       
8VLQJGDWDEDVHKDQGOHV             
8VLQJWKHDFWLYHGDWDEDVH            

PROGRAMMER’S GUIDE iii


Chapter 4 Working with Transactions 'HFODULQJDQGFUHDWLQJDWDEOH        
6WDUWLQJWKHGHIDXOWWUDQVDFWLRQ           &UHDWLQJDYLHZ                 
6WDUWLQJZLWKRXW6(775$16$&7,21     &UHDWLQJDYLHZIRU6(/(&7        
6WDUWLQJZLWK6(775$16$&7,21       &UHDWLQJDYLHZIRUXSGDWH          
6WDUWLQJDQDPHGWUDQVDFWLRQ            &UHDWLQJDQLQGH[                
1DPLQJWUDQVDFWLRQV               3UHYHQWLQJGXSOLFDWHLQGH[HQWULHV      
'HFODULQJWUDQVDFWLRQQDPHV         6SHFLI\LQJLQGH[VRUWRUGHU         
,QLWLDOL]LQJWUDQVDFWLRQQDPHV         &UHDWLQJJHQHUDWRUV               
6SHFLI\LQJ6(775$16$&7,21EHKDYLRU   'URSSLQJPHWDGDWD                
$FFHVVPRGH                  'URSSLQJDQLQGH[               
,VRODWLRQOHYHO                 'URSSLQJDYLHZ                 
/RFNUHVROXWLRQ                'URSSLQJDWDEOH                
5(6(59,1*FODXVH             $OWHULQJPHWDGDWD                 
86,1*FODXVH                 $OWHULQJDWDEOH                 
8VLQJWUDQVDFWLRQQDPHVLQGDWDVWDWHPHQWV    $GGLQJDQHZFROXPQWRDWDEOH       
(QGLQJDWUDQVDFWLRQ                 'URSSLQJDQH[LVWLQJFROXPQ        
8VLQJ&200,7                 0RGLI\LQJDFROXPQ             
6SHFLI\LQJWUDQVDFWLRQQDPHV         $OWHULQJDYLHZ                  
&RPPLWWLQJZLWKRXWIUHHLQJDWUDQVDFWLRQ  $OWHULQJDQLQGH[                
8VLQJ52//%$&.               
Chapter 6 Working with Data
:RUNLQJZLWKPXOWLSOHWUDQVDFWLRQV        
6XSSRUWHGGDWDW\SHV                
7KHGHIDXOWWUDQVDFWLRQ             
8VLQJFXUVRUV                   8QGHUVWDQGLQJ64/H[SUHVVLRQV          
8VLQJWKHVWULQJRSHUDWRULQH[SUHVVLRQV    
$PXOWLWUDQVDFWLRQH[DPSOH          
8VLQJDULWKPHWLFRSHUDWRUVLQH[SUHVVLRQV   
:RUNLQJZLWKPXOWLSOHWUDQVDFWLRQVLQ'64/   
0RGLI\LQJWUDQVDFWLRQEHKDYLRUZLWK ´"µ     8VLQJORJLFDORSHUDWRUVLQH[SUHVVLRQV     
8VLQJFRPSDULVRQRSHUDWRUVLQH[SUHVVLRQV  
Chapter 5 Working with Data 8VLQJ%(7:((1              
Definition Statements 8VLQJ&217$,1,1*           
&UHDWLQJPHWDGDWD                  8VLQJ,1                   
&UHDWLQJDGDWDEDVH                8VLQJ/,.(                 
2SWLRQDOSDUDPHWHUV              8VLQJ,618//               
6SHFLI\LQJDGHIDXOWFKDUDFWHUVHW       8VLQJ67$57,1*:,7+          
&UHDWLQJDGRPDLQ                 8VLQJ$//                  
&UHDWLQJDWDEOH                  8VLQJ$1<DQG620(           
&UHDWLQJDFRPSXWHGFROXPQ        

iv INTERBASE 5
8VLQJ(;,676                 8SGDWLQJWKURXJKFXUVRUV          
8VLQJ6,1*8/$5              2SHQLQJDFXUVRU               
'HWHUPLQLQJSUHFHGHQFHRIRSHUDWRUV     )HWFKLQJURZVZLWKDFXUVRU          
3UHFHGHQFHDPRQJRSHUDWRUV         5HWULHYLQJLQGLFDWRUVWDWXV          
&KDQJLQJHYDOXDWLRQRUGHURIRSHUDWRUV    5HIHWFKLQJURZVZLWKDFXUVRU        
8VLQJ&$67 IRUGDWDW\SHFRQYHUVLRQV    &ORVLQJWKHFXUVRU               
8VLQJ833(5 RQWH[WGDWD          $FRPSOHWHFXUVRUH[DPSOH          
8QGHUVWDQGLQJGDWDUHWULHYDOZLWK6(/(&7    6HOHFWLQJURZVZLWK18//YDOXHV       
/LVWLQJFROXPQVWRUHWULHYHZLWK6(/(&7   /LPLWDWLRQVRQ18//YDOXHV        
5HWULHYLQJDOLVWRIFROXPQV          6HOHFWLQJURZVWKURXJKDYLHZ         
5HWULHYLQJDOOFROXPQV             6HOHFWLQJPXOWLSOHURZVLQ'64/         
5HWULHYLQJDJJUHJDWHFROXPQLQIRUPDWLRQ  'HFODULQJD'64/FXUVRU           
0XOWLWDEOH6(/(&7VWDWHPHQWV       2SHQLQJD'64/FXUVRU           
6SHFLI\LQJWUDQVDFWLRQQDPHV         )HWFKLQJURZVZLWKD'64/FXUVRU      
6SHFLI\LQJKRVWYDULDEOHVZLWK,172      -RLQLQJWDEOHV                    
/LVWLQJWDEOHVWRVHDUFKZLWK)520      &KRRVLQJMRLQFROXPQV            
/LVWLQJDVLQJOHWDEOHRUYLHZ         8VLQJLQQHUMRLQV               
/LVWLQJPXOWLSOHWDEOHV             &UHDWLQJHTXLMRLQV              
'HFODULQJDQGXVLQJFRUUHODWLRQQDPHV    -RLQVEDVHGRQFRPSDULVRQRSHUDWRUV    
5HVWULFWLQJURZUHWULHYDOZLWK:+(5(    &UHDWLQJVHOIMRLQV              
:KDWLVDVHDUFKFRQGLWLRQ"          8VLQJRXWHUMRLQV               
6WUXFWXUHRIDVHDUFKFRQGLWLRQ        8VLQJDOHIWRXWHUMRLQ            
&ROODWLRQRUGHULQFRPSDULVRQV        8VLQJDULJKWRXWHUMRLQ           
6RUWLQJURZVZLWK25'(5%<         8VLQJDIXOORXWHUMRLQ            
25'(5%<ZLWKPXOWLSOHFROXPQV     8VLQJQHVWHGMRLQV               
&ROODWLRQRUGHULQDQ25'(5%<FODXVH   8VLQJVXETXHULHV                  
*URXSLQJURZVZLWK*5283%<       6LPSOHVXETXHULHV               
&ROODWLRQRUGHULQD*5283%<FODXVH   &RUUHODWHGVXETXHULHV             
/LPLWDWLRQVRI*5283%<          ,QVHUWLQJGDWD                    
5HVWULFWLQJJURXSHGURZVZLWK+$9,1*   8VLQJ9$/8(6WRLQVHUWFROXPQV      
$SSHQGLQJWDEOHVZLWK81,21        8VLQJ6(/(&7WRLQVHUWFROXPQV      
6SHFLI\LQJDTXHU\SODQZLWK3/$1      ,QVHUWLQJURZVZLWK18//FROXPQYDOXHV  
6HOHFWLQJDVLQJOHURZ                ,JQRULQJDFROXPQ              
6HOHFWLQJPXOWLSOHURZV               $VVLJQLQJD18//YDOXHWRDFROXPQ    
'HFODULQJDFXUVRU               8VLQJLQGLFDWRUYDULDEOHV           

PROGRAMMER’S GUIDE v
,QVHUWLQJGDWDWKURXJKDYLHZ          )LOWHULQJ%OREGDWD                 
6SHFLI\LQJWUDQVDFWLRQQDPHVLQDQ,16(57  8VLQJWKHVWDQGDUG,QWHU%DVHWH[WILOWHUV   
8SGDWLQJGDWD                    8VLQJDQH[WHUQDO%OREILOWHU         
8SGDWLQJPXOWLSOHURZV             'HFODULQJDQH[WHUQDOILOWHUWRWKHGDWDEDVH 
8VLQJDVHDUFKHGXSGDWH            8VLQJDILOWHUWRUHDGDQGZULWH%OREGDWD  
8VLQJDSRVLWLRQHGXSGDWH           ,QYRNLQJDILOWHULQDQDSSOLFDWLRQ      
18//LQJFROXPQVZLWK83'$7(       :ULWLQJDQH[WHUQDO%OREILOWHU           
8SGDWLQJWKURXJKDYLHZ            )LOWHUW\SHV                   
6SHFLI\LQJWUDQVDFWLRQQDPHVLQ83'$7(   5HDGRQO\DQGZULWHRQO\ILOWHUV        
'HOHWLQJGDWD                     'HILQLQJWKHILOWHUIXQFWLRQ          
'HOHWLQJPXOWLSOHURZV             'HILQLQJWKH%OREFRQWUROVWUXFWXUH     
8VLQJDVHDUFKHGGHOHWH            3URJUDPPLQJILOWHUIXQFWLRQDFWLRQV     
8VLQJDSRVLWLRQHGGHOHWH           7HVWLQJWKHIXQFWLRQUHWXUQYDOXH      
'HOHWLQJWKURXJKDYLHZ           
Chapter 9 Using Arrays
6SHFLI\LQJWUDQVDFWLRQQDPHVLQD'(/(7( 
&UHDWLQJDUUD\V                   
Chapter 7 Working with Dates 0XOWLGLPHQVLRQDODUUD\V           
6HOHFWLQJGDWHV                    6SHFLI\LQJVXEVFULSWUDQJHV          
,QVHUWLQJGDWHV                    $FFHVVLQJDUUD\V                  
8SGDWLQJGDWHV                    6HOHFWLQJGDWDIURPDQDUUD\          
8VLQJ&$67 WRFRQYHUWGDWHV           ,QVHUWLQJGDWDLQWRDQDUUD\          
8VLQJGDWHOLWHUDOV                  6HOHFWLQJIURPDQDUUD\VOLFH          
8SGDWLQJGDWDLQDQDUUD\VOLFH        
Chapter 8 Working with Blob Data 7HVWLQJDYDOXHLQDVHDUFKFRQGLWLRQ     
:KDWLVD%ORE"                   8VLQJKRVWYDULDEOHVLQDUUD\VXEVFULSWV    
+RZDUH%OREGDWDVWRUHG"             8VLQJDULWKPHWLFH[SUHVVLRQVZLWKDUUD\V   
%OREVXEW\SHV                 
%OREGDWDEDVHVWRUDJH              Chapter 10 Working with
%OREVHJPHQWOHQJWK              User-Defined Functions
2YHUULGLQJVHJPHQWOHQJWK           &UHDWLQJD8')                  
$FFHVVLQJ%OREGDWDZLWK64/           :ULWLQJDQGFRPSLOLQJIXQFWLRQV          
6HOHFWLQJ%OREGDWD               :ULWLQJDIXQFWLRQPRGXOH          
,QVHUWLQJ%OREGDWD               6SHFLI\LQJSDUDPHWHUV            
8SGDWLQJ%OREGDWD               6SHFLI\LQJDUHWXUQYDOXH           
'HOHWLQJ%OREGDWD               :ULWLQJD%ORE8')              
$FFHVVLQJ%OREGDWDZLWK$3,FDOOV         &UHDWLQJD%OREFRQWUROVWUXFWXUH      

vi INTERBASE 5
$%ORE8')H[DPSOH             7HVWLQJ64/&2'(GLUHFWO\          
&RPSLOLQJDIXQFWLRQPRGXOH         &RPELQLQJHUURUKDQGOLQJWHFKQLTXHV    
&UHDWLQJD8')OLEUDU\               *XLGHOLQHVIRUHUURUKDQGOLQJ         
0RGLI\LQJD8')OLEUDU\            $GGLWLRQDO,QWHU%DVHHUURUKDQGOLQJ        
'HFODULQJD8')WRDGDWDEDVH           'LVSOD\LQJHUURUPHVVDJHV           
'HFODULQJD%ORE8')             &DSWXULQJ64/HUURUPHVVDJHV        
&DOOLQJD8')                    &DSWXULQJ,QWHU%DVHHUURUPHVVDJHV     
8VLQJD8')ZLWK6(/(&7          +DQGOLQJ,QWHU%DVHHUURUFRGHV        
8VLQJD8')ZLWK,16(57         
8VLQJD8')ZLWK83'$7(          Chapter 14 Using Dynamic SQL
8VLQJD8')ZLWK'(/(7(          2YHUYLHZRIWKH'64/SURJUDPPLQJSURFHVV  
'64/OLPLWDWLRQV                 
Chapter 11 Working with Stored Procedures $FFHVVLQJGDWDEDVHV              
8VLQJVWRUHGSURFHGXUHV               +DQGOLQJWUDQVDFWLRQV             
3URFHGXUHVDQGWUDQVDFWLRQV          &UHDWLQJDGDWDEDVH              
6HFXULW\IRUSURFHGXUHV             3URFHVVLQJ%OREGDWD             
8VLQJVHOHFWSURFHGXUHV               3URFHVVLQJDUUD\GDWD             
&DOOLQJDVHOHFWSURFHGXUH            :ULWLQJD'64/DSSOLFDWLRQ            
8VLQJDVHOHFWSURFHGXUHZLWKFXUVRUV     64/VWDWHPHQWV'64/FDQSURFHVV     
8VLQJH[HFXWDEOHSURFHGXUHV            64/FKDUDFWHUVWULQJV             
([HFXWLQJDSURFHGXUH             9DOXHSDUDPHWHUVLQVWDWHPHQWVWULQJV     
,QGLFDWRUYDULDEOHV               8QGHUVWDQGLQJWKH;64/'$           
([HFXWLQJDSURFHGXUHLQD ;64/'$ILHOGGHVFULSWLRQV          
'64/DSSOLFDWLRQ            ;64/9$5ILHOGGHVFULSWLRQV         
,QSXWGHVFULSWRUV               
Chapter 12 Working with Events
2XWSXWGHVFULSWRUV              
8QGHUVWDQGLQJWKHHYHQWPHFKDQLVP       
8VLQJWKH;64/'$B/(1*7+PDFUR   
6LJQDOLQJHYHQWRFFXUUHQFHV            
64/GDWDW\SHPDFURFRQVWDQWV        
5HJLVWHULQJLQWHUHVWLQHYHQWV           
+DQGOLQJYDU\LQJVWULQJGDWDW\SHV       
5HJLVWHULQJLQWHUHVWLQPXOWLSOHHYHQWV       
180(5,&DQG'(&,0$/GDWDW\SHV    
:DLWLQJIRUHYHQWVZLWK(9(17:$,7     
&RHUFLQJGDWDW\SHV              
5HVSRQGLQJWRHYHQWV               
&RHUFLQJFKDUDFWHUGDWDW\SHV         
Chapter 13 Error Handling and Recovery &RHUFLQJQXPHULFGDWDW\SHV         
6WDQGDUGHUURUKDQGOLQJ               6HWWLQJD18//LQGLFDWRU          
:+(1(9(5VWDWHPHQWV           $OLJQLQJQXPHULFDOGDWD            

PROGRAMMER’S GUIDE vii


'64/SURJUDPPLQJPHWKRGV           Chapter 15 Preprocessing, Compiling,
0HWKRG1RQTXHU\VWDWHPHQWV and Linking
ZLWKRXWSDUDPHWHUV            3UHSURFHVVLQJ                   
8VLQJ(;(&87(,00(',$7(       8VLQJJSUH                   
8VLQJ35(3$5(DQG(;(&87(      /DQJXDJHVZLWFKHV              
0HWKRG1RQTXHU\VWDWHPHQWV 2SWLRQVZLWFKHV               
ZLWKSDUDPHWHUV            
([DPSOHV                   
&UHDWLQJWKHLQSXW;64/'$        
8VLQJDILOHH[WHQVLRQWRVSHFLI\ODQJXDJH   
3UHSDULQJDQGH[HFXWLQJDVWDWHPHQW 6SHFLI\LQJWKHVRXUFHILOH           
VWULQJZLWKSDUDPHWHUV        
&RPSLOLQJDQGOLQNLQJ               
5HH[HFXWLQJWKHVWDWHPHQWVWULQJ      
&RPSLOLQJDQ$GDSURJUDP          
0HWKRG4XHU\VWDWHPHQWV
ZLWKRXWSDUDPHWHUV            /LQNLQJ                     
3UHSDULQJWKHRXWSXW;64/'$       
Appendix A InterBase Document
3UHSDULQJDTXHU\VWDWHPHQWVWULQJ      Conventions
([HFXWLQJDVWDWHPHQWVWULQJZLWKLQWKH
7KH,QWHU%DVHGRFXPHQWDWLRQVHW         
FRQWH[W RIDFXUVRU          
3ULQWLQJFRQYHQWLRQV                
5HH[HFXWLQJDTXHU\VWDWHPHQWVWULQJ    
6\QWD[FRQYHQWLRQV                 
0HWKRG4XHU\VWDWHPHQWV
LWKSDUDPHWHUV             
3UHSDULQJWKHLQSXW;64/'$       
3UHSDULQJWKHRXWSXW;64/'$       
3UHSDULQJDTXHU\VWDWHPHQWVWULQJ
ZLWKSDUDPHWHUV            
([HFXWLQJDTXHU\VWDWHPHQWVWULQJZLWKLQWKH
FRQWH[WRIDFXUVRU          
5HH[HFXWLQJDTXHU\VWDWHPHQWVWULQJ
LWKSDUDPHWHUV             

viii INTERBASE 5
List of Tables

7DEOH &KDSWHUVLQWKH,QWHU%DVH3URJUDPPHU·V*XLGH             


7DEOH &211(&7V\QWD[VXPPDU\                       
7DEOH 64/WUDQVDFWLRQPDQDJHPHQWVWDWHPHQWV                  
7DEOH 'HIDXOWWUDQVDFWLRQGHIDXOWEHKDYLRU                    
7DEOH 6(775$16$&7,21SDUDPHWHUV                    
7DEOH ,62/$7,21/(9(/RSWLRQV                       
7DEOH ,QWHU%DVHPDQDJHPHQWRIFODVVLFWUDQVDFWLRQFRQIOLFWV          
7DEOH ,VRODWLRQOHYHO,QWHUDFWLRQZLWK6(/(&7DQG83'$7(         
7DEOH 7DEOHUHVHUYDWLRQRSWLRQVIRUWKH5(6(59,1*FODXVH          
7DEOH 'DWDGHILQLWLRQVWDWHPHQWVVXSSRUWHGIRUHPEHGGHGDSSOLFDWLRQV    
7DEOH 'DWDW\SHVVXSSRUWHGE\,QWHU%DVH                     
7DEOH (OHPHQWVRI64/H[SUHVVLRQV                        
7DEOH $ULWKPHWLFRSHUDWRUV                            
7DEOH ,QWHU%DVHFRPSDULVRQRSHUDWRUVUHTXLULQJVXETXHULHV           
7DEOH 2SHUDWRUSUHFHGHQFHE\RSHUDWRUW\SH                   
7DEOH 0DWKHPDWLFDORSHUDWRUSUHFHGHQFH                     
7DEOH &RPSDULVRQRSHUDWRUSUHFHGHQFH                      
7DEOH /RJLFDORSHUDWRUSUHFHGHQFH                        
7DEOH &RPSDWLEOHGDWDW\SHVIRU&$67                      
7DEOH 6(/(&7VWDWHPHQWFODXVHV                        
7DEOH $JJUHJDWHIXQFWLRQVLQ64/                         
7DEOH (OHPHQWVRI:+(5(FODXVH6($5&+FRQGLWLRQV             
7DEOH %/2%VXEW\SHVGHILQHGE\,QWHU%DVH                   
7DEOH $3,%OREFDOOV                                
7DEOH LVFBEOREBFWOVWUXFWXUHILHOGGHVFULSWLRQV                  
7DEOH %OREDFFHVVRSHUDWLRQV                          
7DEOH %OREILOWHUVWDWXVYDOXHV                           
7DEOH '(&/$5((;7(51$/)81&7,21SDUDPHWHUV           
7DEOH 3RVVLEOH64/&2'(YDOXHV                        
7DEOH ;64/'$ILHOGGHVFULSWLRQV                         
7DEOH ;64/9$5ILHOGGHVFULSWLRQV                        
7DEOH 64/GDWDW\SHVPDFURH[SUHVVLRQVDQG&GDWDW\SHV            
7DEOH 64/VWDWHPHQWVWULQJVDQGUHFRPPHQGHGSURFHVVLQJPHWKRGV      

PROGRAMMER’S GUIDE ix
LIST OF TABLES

7DEOH JSUHODQJXDJHVZLWFKHVDYDLODEOHRQDOOSODWIRUPV             


7DEOH $GGLWLRQDOJSUHODQJXDJHVZLWFKHV                    
7DEOH JSUHRSWLRQVZLWFKHV                            
7DEOH /DQJXDJHVSHFLILFJSUHRSWLRQVZLWFKHV                  
7DEOH )LOHH[WHQVLRQVIRUODQJXDJHVSHFLILFDWLRQ                 
7DEOH$ %RRNVLQWKH,QWHU%DVHGRFXPHQWDWLRQVHW              
7DEOH 7H[WFRQYHQWLRQV                             
7DEOH 6\QWD[FRQYHQWLRQV                            

x INTERBASE 5
List of Figures

)LJXUH 5HODWLRQVKLSRID%ORE,'WR%OREVHJPHQWVLQDGDWDEDVH        


)LJXUH )LOWHULQJIURPORZHUFDVHWRXSSHUFDVH                  
)LJXUH )LOWHULQJIURPXSSHUFDVHWRORZHUFDVH                  
)LJXUH )LOWHULQWHUDFWLRQZLWKDQDSSOLFDWLRQDQGDGDWDEDVH           
)LJXUH ;64/'$DQG;64/9$5UHODWLRQVKLS                  

PROGRAMMER’S GUIDE xi
CHAPTER

Using the Chapter1


1
Programmer’s Guide

7KH,QWHU%DVH3URJUDPPHU·V*XLGHLVDWDVNRULHQWHGH[SODQDWLRQRIKRZWRZULWHSUHSURFHVV
FRPSLOHDQGOLQNHPEHGGHG64/DQG'64/GDWDEDVHDSSOLFDWLRQVXVLQJ,QWHU%DVHDQGDKRVW
SURJUDPPLQJODQJXDJHHLWKHU&RU&7KLVFKDSWHUGHVFULEHVZKRVKRXOGUHDGWKLVERRNDQG
SURYLGHVDEULHIRYHUYLHZRILWVFKDSWHUV

Who should use this guide


7KH,QWHU%DVH3URJUDPPHU·V*XLGHLVLQWHQGHGIRUGDWDEDVHDSSOLFDWLRQVSURJUDPPHUV
,W DVVXPHVDJHQHUDONQRZOHGJHRI
g 64/
g 5HODWLRQDOGDWDEDVHSURJUDPPLQJ
g &SURJUDPPLQJ
7KH3URJUDPPHU·V*XLGHDVVXPHVOLWWOHRUQRSUHYLRXVH[SHULHQFHZLWK,QWHU%DVH6HHWKH
2SHUDWLRQV*XLGHIRUDQLQWURGXFWLRQWR,QWHU%DVHDQGWKH/DQJXDJH5HIHUHQFHIRUDQLQWURGXFWLRQ
WR64/

1
CHAPTER 1 USING THE PROGRAMMER’S GUIDE

Note 7KH3URJUDPPHU·V*XLGHIRFXVHVRQHPEHGGHG64/DQG'64/SURJUDPPLQJLQ&RU
&'HYHORSHUVXVLQJ%RUODQG'HOSKLZLOOILQGQR'HOSKLVSHFLILFWRSLFVLQWKLVERRN

Topics covered in this guide


7KHIROORZLQJWDEOHSURYLGHVDEULHIGHVFULSWLRQRIHDFKFKDSWHULQWKLV3URJUDPPHU·V*XLGH

Chapter Description
Chapter 1, “Using the Programmer’s Guide” Introduces the structure of the book and describes its intended
audience.
Chapter 2, “Application Requirements” Describes elements common to programming all SQL and DSQL
applications.
Chapter 3, “Working with Databases” Describes using SQL statements that deal with databases.
Chapter 4, “Working with Transactions” Explains how to use and control transactions with SQL statements.
Chapter 5, “Working with Data Definition Describes how to embed SQL data definition statements in
Statements” applications.
Chapter 6, “Working with Data” Explains how to select, insert, update, and delete standard SQL data in
applications.
Chapter 7, “Working with Dates” Describes how to select, insert, update, and delete DATE data in
applications.
Chapter 8, “Working with Blob Data” Describes how to select, insert, update, and delete Blob data in
applications.
Chapter 9, “Using Arrays” Describes how to select, insert, update, and delete array data in
applications.
Chapter 10, “Working with User-Defined Functions” Describes how to write UDFs, how to call UDFs in applications, how to
write Blob filters, and how to create Blob filter libraries.
Chapter 11, “Working with Stored Procedures” Explains how to call stored procedures in applications.
Chapter 12, “Working with Events” Explains how triggers interact with applications. Describes how to
register interest in events, wait on them, and respond to them in
applications.
Chapter 13, “Error Handling and Recovery” Describes how to trap and handle SQL statement errors in
applications.
TABLE 1.1 Chapters in the InterBase 5 Programmer’s Guide

2 INTERBASE 5
SAMPLE DATABASE AND APPLICATIONS

Chapter Description
Chapter 14, “Using Dynamic SQL” Describes how to write DSQL applications.
Chapter 15, “Preprocessing, Compiling, Describes how to convert source code into an executable application.
and Linking”
Appendix A, “InterBase Document Conventions” Lists typefaces and special characters used in this book to describe
syntax and identify object types.
TABLE 1.1 Chapters in the InterBase 5 Programmer’s Guide (continued)

Sample database and applications


7KH,QWHU%DVHH[DPSOHVVXEGLUHFWRU\FRQWDLQVVHYHUDOXVHIXOLWHPVZRUWKQRWLQJLQFOXGLQJ
g 7KHLEBXGIVTOILOHZKLFKGHFODUHVWKH8')VLQWKHOLEUDU\SURYLGHGE\,QWHU%DVHWKHOLEUDU\
RI8')VLVLQWKH,QWHU%DVHOLEVXEGLUHFWRU\DQGLVQDPHGLEBXGIGOORQ:LQWHOSODWIRUPVDQG
LEBXGIRQ81,;SODWIRUPV
g $VDPSOHGDWDEDVHHPSOR\HHJGE
g 6DPSOHDSSOLFDWLRQVRXUFHFRGHZKLFKSURGXFHVVHYHUDOVDPSOHDSSOLFDWLRQVZKHQFRPSLOHG
VHHWKHPDNHILOHDQGWKHUHDGPHLQWKHH[DPSOHVGLUHFWRU\IRUPRUHLQIRUPDWLRQDERXWWKH
VDPSOHDSSOLFDWLRQVDQGKRZWRFRPSLOHWKHP
7KH3URJUDPPHU·V*XLGHPDNHVXVHRIWKHVDPSOHGDWDEDVHDQGVRXUFHFRGHIRULWVH[DPSOHV
ZKHUHYHUSRVVLEOH

PROGRAMMER’S GUIDE 3
CHAPTER

Application Requirements
Chapter2
2
7KLVFKDSWHUGHVFULEHVSURJUDPPLQJUHTXLUHPHQWVIRU,QWHU%DVH64/DQGG\QDPLF64/
'64/ DSSOLFDWLRQV0DQ\RIWKHVHUHTXLUHPHQWVPD\DOVRDIIHFWGHYHORSHUVPRYLQJH[LVWLQJ
DSSOLFDWLRQVWR,QWHU%DVH

Requirements for all applications


$OOHPEHGGHGDSSOLFDWLRQVPXVWLQFOXGHFHUWDLQGHFODUDWLRQVDQGVWDWHPHQWVWRHQVXUHSURSHU
KDQGOLQJE\WKH,QWHU%DVHSUHSURFHVVRUgpreDQGWRHQDEOHFRPPXQLFDWLRQEHWZHHQ64/
DQGWKHKRVWODQJXDJHLQZKLFKWKHDSSOLFDWLRQLVZULWWHQ(YHU\DSSOLFDWLRQPXVW
g 'HFODUHKRVWYDULDEOHVWRXVHIRUGDWDWUDQVIHUEHWZHHQ64/DQGWKHDSSOLFDWLRQ
g 'HFODUHDQGVHWWKHGDWDEDVHVDFFHVVHGE\WKHSURJUDP
g &UHDWHWUDQVDFWLRQKDQGOHVIRUHDFKQRQGHIDXOWWUDQVDFWLRQXVHGLQWKHSURJUDP
g ,QFOXGH64/ DQGRSWLRQDOO\'64/ VWDWHPHQWV
g 3URYLGHHUURUKDQGOLQJDQGUHFRYHU\
g &ORVHDOOWUDQVDFWLRQVDQGGDWDEDVHVEHIRUHHQGLQJWKHSURJUDP
'\QDPLF64/DSSOLFDWLRQVWKRVHDSSOLFDWLRQVWKDWEXLOG64/VWDWHPHQWVDWUXQWLPHRU
HQDEOHXVHUVWREXLOGWKHPKDYHDGGLWLRQDOUHTXLUHPHQWV)RUPRUHLQIRUPDWLRQDERXW'64/
UHTXLUHPHQWVVHH´'64/UHTXLUHPHQWVµRQSDJH 

5
CHAPTER 2 APPLICATION REQUIREMENTS

)RUPRUHLQIRUPDWLRQDERXWXVLQJgpreVHH&KDSWHU´3UHSURFHVVLQJ&RPSLOLQJ
DQG /LQNLQJµ

Porting considerations for SQL


:KHQSRUWLQJH[LVWLQJ64/DSSOLFDWLRQVWR,QWHU%DVHRWKHUFRQVLGHUDWLRQVPD\EHQHFHVVDU\
)RUH[DPSOHPDQ\64/YDULDQWVUHTXLUHWKDWKRVWYDULDEOHVEHGHFODUHGEHWZHHQ%(*,1
'(&/$5(6(&7,21DQG(1''(&/$5(6(&7,21VWDWHPHQWV,QWHU%DVHKDVQRVXFK
UHTXLUHPHQWVEXWgpreFDQFRUUHFWO\KDQGOHVHFWLRQGHFODUDWLRQVIURPSRUWHGDSSOLFDWLRQV
)RUDGGLWLRQDOSRUWDELOLW\GHFODUHDOOKRVWODQJXDJHYDULDEOHVZLWKLQVHFWLRQV

Porting considerations for DSQL


:KHQSRUWLQJH[LVWLQJ'64/DSSOLFDWLRQVWR,QWHU%DVHVWDWHPHQWVWKDWXVHDQRWKHUYHQGRU·V
64/GHVFULSWRUDUHD 64/'$ PXVWEHPRGLILHGWRDFFRPPRGDWHWKHH[WHQGHG64/'$
;64/'$ XVHGE\,QWHU%DVH

Declaring host variables


$KRVWYDULDEOHLVDVWDQGDUGKRVWODQJXDJHYDULDEOHXVHGWRKROGYDOXHVUHDGIURPDGDWDEDVH
WRDVVHPEOHYDOXHVWRZULWHWRDGDWDEDVHRUWRVWRUHYDOXHVGHVFULELQJGDWDEDVHVHDUFK
FRQGLWLRQV64/XVHVKRVWYDULDEOHVLQWKHIROORZLQJVLWXDWLRQV
g 'XULQJGDWDUHWULHYDO64/PRYHVWKHYDOXHVLQGDWDEDVHILHOGVLQWRKRVWYDULDEOHVZKHUHWKH\
FDQEHYLHZHGDQGPDQLSXODWHG
g :KHQDXVHULVSURPSWHGIRULQIRUPDWLRQKRVWYDULDEOHVDUHXVHGWRKROGWKHGDWDXQWLOLWFDQ
EHSDVVHGWR,QWHU%DVHLQDQ64/,16(57RU83'$7(VWDWHPHQW
g :KHQVSHFLI\LQJVHDUFKFRQGLWLRQVLQD6(/(&7VWDWHPHQWFRQGLWLRQVFDQEHHQWHUHGGLUHFWO\
RULQDKRVWYDULDEOH)RUH[DPSOHERWKRIWKHIROORZLQJ64/VWDWHPHQWIUDJPHQWVDUHYDOLG
:+(5(FODXVHV7KHVHFRQGXVHVDKRVWODQJXDJHYDULDEOHFRXQWU\IRUFRPSDULVRQZLWKD
FROXPQ&28175<
… WHERE COUNTRY = "Mexico";
… WHERE COUNTRY = :country;

6 INTERBASE 5
REQUIREMENTS FOR ALL APPLICATIONS

2QHKRVWYDULDEOHPXVWEHGHFODUHGIRUHYHU\FROXPQRIGDWDDFFHVVHGLQDGDWDEDVH+RVW
YDULDEOHVPD\HLWKHUEHGHFODUHGJOREDOO\OLNHDQ\RWKHUVWDQGDUGKRVWODQJXDJHYDULDEOHRU
PD\DSSHDUZLWKLQDQ64/VHFWLRQGHFODUDWLRQZLWKRWKHUJOREDOGHFODUDWLRQV)RUPRUH
LQIRUPDWLRQDERXWUHDGLQJIURPDQGZULWLQJWRKRVWYDULDEOHVLQ64/SURJUDPVVHH&KDSWHU
´:RUNLQJZLWK'DWDµ
+RVWYDULDEOHVXVHGLQ64/SURJUDPVDUHGHFODUHGMXVWOLNHVWDQGDUGODQJXDJHYDULDEOHV7KH\
IROORZDOOVWDQGDUGKRVWODQJXDJHUXOHVIRUGHFODUDWLRQLQLWLDOL]DWLRQDQGPDQLSXODWLRQ)RU
H[DPSOHLQ&YDULDEOHVPXVWEHGHFODUHGEHIRUHWKH\FDQEHXVHGDVKRVWYDULDEOHVLQ64/
VWDWHPHQWV
int empno; char fname[26], lname[26];
)RUFRPSDWLELOLW\ZLWKRWKHU64/YDULDQWVKRVWYDULDEOHVFDQDOVREHGHFODUHGEHWZHHQ
%(*,1'(&/$5(6(&7,21DQG(1''(&/$5(6(&7,21VWDWHPHQWV

4 6HFWLRQGHFODUDWLRQV
0DQ\64/LPSOHPHQWDWLRQVH[SHFWKRVWYDULDEOHVWREHGHFODUHGEHWZHHQ%(*,1'(&/$5(
6(&7,21DQG(1''(&/$5(6(&7,21VWDWHPHQWV)RUSRUWDELOLW\DQGFRPSDWLELOLW\
,QWHU%DVHVXSSRUWVVHFWLRQGHFODUDWLRQVXVLQJWKHIROORZLQJV\QWD[
EXEC SQL
BEGIN DECLARE SECTION;
<hostvar>;
. . .
EXEC SQL
END DECLARE SECTION;
)RUH[DPSOHWKHIROORZLQJ&FRGHIUDJPHQWGHFODUHVWKUHHKRVWYDULDEOHVHPSQRIQDPHDQG
OQDPHZLWKLQDVHFWLRQGHFODUDWLRQ
EXEC SQL
BEGIN DECLARE SECTION;
int empno;
char fname[26];
char lname[26];
EXEC SQL
END DECLARE SECTION;

$GGLWLRQDOKRVWODQJXDJHYDULDEOHVQRWXVHGLQ64/VWDWHPHQWVFDQEHGHFODUHGRXWVLGH
'(&/$5(6(&7,21 VWDWHPHQWV

PROGRAMMER’S GUIDE 7
CHAPTER 2 APPLICATION REQUIREMENTS

4 8VLQJ%$6('21WRGHFODUHYDULDEOHV
,QWHU%DVHVXSSRUWVDGHFODUDWLYHFODXVH%$6('21IRUFUHDWLQJ&ODQJXDJHFKDUDFWHU
YDULDEOHVEDVHGRQFROXPQGHILQLWLRQVLQDGDWDEDVH8VLQJ%$6('21HQVXUHVWKDWWKH
UHVXOWLQJKRVWODQJXDJHYDULDEOHLVODUJHHQRXJKWRKROGWKHPD[LPXPQXPEHURIFKDUDFWHUV
LQD&+$5RU9$5&+$5GDWDEDVHFROXPQSOXVDQH[WUDE\WHIRUWKHQXOOWHUPLQDWLQJ
FKDUDFWHUH[SHFWHGE\PRVW&VWULQJIXQFWLRQV
%$6('21XVHVWKHIROORZLQJV\QWD[
BASED ON <dbcolumn> hostvar;

)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVGHFODUHWZRKRVWYDULDEOHVIQDPHDQGOQDPHEDVHGRQ
WZRFROXPQGHILQLWLRQV),5671$0(DQG/$671$0(LQDQHPSOR\HHGDWDEDVH
BASED ON EMP.FIRSTNAME fname;
BASED ON EMP.LASTNAME lname;

(PEHGGHGLQD&RU&SURJUDPWKHVHVWDWHPHQWVJHQHUDWHWKHIROORZLQJKRVWYDULDEOH
GHFODUDWLRQVGXULQJSUHSURFHVVLQJ
char fname[26];
char lname[26];

7RXVH%$6('21IROORZWKHVHVWHSV
 8VH6(7'$7$%$6(WRVSHFLI\WKHGDWDEDVHIURPZKLFKFROXPQGHILQLWLRQVDUH
WREHGUDZQ
 8VH&211(&7WRDWWDFKWRWKHGDWDEDVH
 'HFODUHDVHFWLRQZLWK%(*,1'(&/$5(6(&7,21
 8VHWKH%$6('21VWDWHPHQWWRGHFODUHDVWULQJYDULDEOHRIWKHDSSURSULDWHW\SH
7KHIROORZLQJVWDWHPHQWVVKRZWKHSUHYLRXV%$6('21GHFODUDWLRQVLQFRQWH[W
EXEC SQL
SET DATABASE EMP = "employee.gdb";
EXEC SQL
CONNECT EMP;
EXEC SQL
BEGIN DECLARE SECTION;
int empno;
BASED ON EMP.FIRSTNAME fname;
BASED ON EMP.LASTNAME lname;
EXEC SQL
END DECLARE SECTION;

8 INTERBASE 5
DECLARING AND INITIALIZING DATABASES

4 +RVWODQJXDJHGDWDVWUXFWXUHV
,IDKRVWODQJXDJHVXSSRUWVGDWDVWUXFWXUHVGDWDILHOGVZLWKLQDVWUXFWXUHFDQFRUUHVSRQGWR
DFROOHFWLRQRIGDWDEDVHFROXPQV)RUH[DPSOHWKHIROORZLQJ&GHFODUDWLRQFUHDWHVD
VWUXFWXUH%,//,1*B$''5(66WKDWFRQWDLQVVL[YDULDEOHVRUGDWDPHPEHUVHDFKRIZKLFK
FRUUHVSRQGVWRDVLPLODUO\QDPHGFROXPQLQDWDEOH
struct
{
char fname[25];
char lname[25];
char street[30];
char city[20];
char state[3];
char zip[11];
} billing_address;

64/UHFRJQL]HVGDWDPHPEHUVLQVWUXFWXUHVEXWLQIRUPDWLRQUHDGIURPRUZULWWHQWRD
VWUXFWXUHPXVWEHUHDGIURPRUZULWWHQWRLQGLYLGXDOGDWDPHPEHUVLQ64/VWDWHPHQWV)RU
H[DPSOHWKHIROORZLQJ64/VWDWHPHQWUHDGVGDWDIURPDWDEOHLQWRYDULDEOHVLQWKH&
VWUXFWXUH%,//,1*B$''5(66
EXEC SQL
SELECT FNAME, LNAME, STREET, CITY, STATE, ZIP
INTO :billing_address.fname, :billing_address.lname,
:billing_address.street, :billing_address.city,
:billing_address.state, :billing_address.zip
FROM ADDRESSES WHERE CITY = "Brighton";

Declaring and initializing databases


$Q64/SURJUDPFDQDFFHVVPXOWLSOH,QWHU%DVHGDWDEDVHVDWWKHVDPHWLPH(DFKGDWDEDVH
XVHGLQDPXOWLSOHGDWDEDVHSURJUDPPXVWEHGHFODUHGDQGLQLWLDOL]HGEHIRUHLWFDQEHDFFHVVHG
LQ64/WUDQVDFWLRQV3URJUDPVWKDWDFFHVVRQO\DVLQJOHGDWDEDVHQHHGQRWGHFODUHWKH
GDWDEDVHRUDVVLJQDGDWDEDVHKDQGOHLILQVWHDGWKH\VSHFLI\DGDWDEDVHRQWKHgpreFRPPDQG
OLQH

,03257$17 '64/SURJUDPVFDQQRWFRQQHFWWRPXOWLSOHGDWDEDVHV
,QWHU%DVHVXSSRUWVWKHIROORZLQJ64/VWDWHPHQWVIRUKDQGOLQJGDWDEDVHV
g 6(7'$7$%$6(GHFODUHVWKHQDPHRIDGDWDEDVHWRDFFHVVDQGDVVLJQVLWWRDGDWDEDVHKDQGOH
g &211(&7 RSHQVDGDWDEDVHVSHFLILHGE\DKDQGOHDQGDOORFDWHVLWV\VWHPUHVRXUFHV

PROGRAMMER’S GUIDE 9
CHAPTER 2 APPLICATION REQUIREMENTS

'DWDEDVHKDQGOHVUHSODFHGDWDEDVHQDPHVLQ&211(&7VWDWHPHQWV7KH\FDQDOVREHXVHGWR
TXDOLI\WDEOHQDPHVZLWKLQWUDQVDFWLRQV)RUDFRPSOHWHGLVFXVVLRQRIGDWDEDVHKDQGOLQJLQ
64/SURJUDPVVHH&KDSWHU´:RUNLQJZLWK'DWDEDVHVµ

Using SET DATABASE


7KH6(7'$7$%$6( VWDWHPHQWLVXVHGWR
g 'HFODUHDGDWDEDVHKDQGOHIRUHDFKGDWDEDVHXVHGLQDQ64/SURJUDP
g $VVRFLDWHDGDWDEDVHKDQGOHZLWKDQDFWXDOGDWDEDVHQDPH7\SLFDOO\DGDWDEDVHKDQGOHLVD
PQHPRQLFDEEUHYLDWLRQRIWKHDFWXDOGDWDEDVHQDPH
6(7'$7$%$6(LQVWDQWLDWHVDKRVWYDULDEOHIRUWKHGDWDEDVHKDQGOHZLWKRXWUHTXLULQJDQ
H[SOLFLWKRVWYDULDEOHGHFODUDWLRQ7KHGDWDEDVHKDQGOHFRQWDLQVDSRLQWHUXVHGWRUHIHUHQFH
WKHGDWDEDVHLQVXEVHTXHQW64/VWDWHPHQWV7RLQFOXGHD6(7'$7$%$6(VWDWHPHQWLQD
SURJUDPXVHWKHIROORZLQJV\QWD[
EXEC SQL
SET DATABASE handle = "<dbname>";

$VHSDUDWHVWDWHPHQWVKRXOGEHXVHGIRUHDFKGDWDEDVH)RUH[DPSOHWKHIROORZLQJ
VWDWHPHQWVGHFODUHDKDQGOH'%IRUWKHHPSOR\HHJGEGDWDEDVHDQGDQRWKHUKDQGOH'%IRU
HPSOR\HHJGE
EXEC SQL
SET DATABASE DB1 = "employee.gdb";
EXEC SQL
SET DATABASE DB2 = "employee2.gdb";

2QFHDGDWDEDVHKDQGOHLVFUHDWHGDQGDVVRFLDWHGZLWKDGDWDEDVHWKHKDQGOHFDQEHXVHGLQ
VXEVHTXHQW64/GDWDEDVHDQGWUDQVDFWLRQVWDWHPHQWVWKDWUHTXLUHLWVXFKDV&211(&7
Note 6(7'$7$%$6(DOVRVXSSRUWVXVHUQDPHDQGSDVVZRUGRSWLRQV)RUDFRPSOHWH
GLVFXVVLRQRI6(7'$7$%$6(RSWLRQVVHH&KDSWHU´:RUNLQJZLWK'DWDEDVHVµ

Using CONNECT
7KH&211(&7VWDWHPHQWDWWDFKHVWRDGDWDEDVHRSHQVWKHGDWDEDVHDQGDOORFDWHVV\VWHP
UHVRXUFHVIRULW$GDWDEDVHPXVWEHRSHQHGEHIRUHLWVWDEOHVFDQEHXVHG7RLQFOXGH
&211(&7LQDSURJUDPXVHWKHIROORZLQJV\QWD[
EXEC SQL
CONNECT handle;

10 INTERBASE 5
DECLARING AND INITIALIZING DATABASES

$VHSDUDWHVWDWHPHQWFDQEHXVHGIRUHDFKGDWDEDVHRUDVLQJOHVWDWHPHQWFDQFRQQHFWWR
PXOWLSOHGDWDEDVHV)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVFRQQHFWWRWZRGDWDEDVHV
EXEC SQL
CONNECT DB1;
EXEC SQL
CONNECT DB2;
7KHQH[WH[DPSOHXVHVDVLQJOH&211(&7WRHVWDEOLVKERWKFRQQHFWLRQV
EXEC SQL
CONNECT DB1, DB2;

2QFHDGDWDEDVHLVFRQQHFWHGLWVWDEOHVFDQEHDFFHVVHGLQVXEVHTXHQWWUDQVDFWLRQV,WVKDQGOH
FDQTXDOLI\WDEOHQDPHVLQ64/DSSOLFDWLRQVEXWQRWLQ'64/DSSOLFDWLRQV)RUDFRPSOHWH
GLVFXVVLRQRI&211(&7RSWLRQVDQGXVLQJGDWDEDVHKDQGOHVVHH&KDSWHU´:RUNLQJZLWK
'DWDEDVHVµ

Working with a single database


,QVLQJOHGDWDEDVHSURJUDPVSUHSURFHVVHGZLWKRXWWKHgpre -mVZLWFK6(7'$7$%$6( DQG
&211(&7 DUHRSWLRQDO7KH-mVZLWFKVXSSUHVVHVDXWRPDWLFJHQHUDWLRQRIWUDQVDFWLRQV
8VLQJ6(7'$7$%$6(DQG&211(&7LVVWURQJO\UHFRPPHQGHGKRZHYHUHVSHFLDOO\DVDZD\
WRPDNHSURJUDPFRGHDVVHOIGRFXPHQWLQJDVSRVVLEOH,I\RXRPLWWKHVHVWDWHPHQWVWDNHWKH
IROORZLQJVWHSV
 ,QVHUWDVHFWLRQGHFODUDWLRQLQWKHSURJUDPFRGHZKHUHJOREDOYDULDEOHVDUH
GHILQHG8VHDQHPSW\VHFWLRQGHFODUDWLRQLIQRKRVWODQJXDJHYDULDEOHVDUHXVHG
LQWKHSURJUDP)RUH[DPSOHWKHIROORZLQJGHFODUDWLRQLOOXVWUDWHVDQHPSW\
VHFWLRQGHFODUDWLRQ
EXEC SQL
BEGIN DECLARE SECTION;
EXEC SQL
END DECLARE SECTION;
 6SHFLI\DGDWDEDVHQDPHRQWKHgpreFRPPDQGOLQHDWSUHFRPSLOHWLPH$
GDWDEDVHQHHGQRWEHVSHFLILHGLIDSURJUDPFRQWDLQVD&5($7('$7$%$6(
VWDWHPHQW
)RUPRUHLQIRUPDWLRQDERXWZRUNLQJZLWKDVLQJOHGDWDEDVHLQDQ64/SURJUDPVHH&KDSWHU
´:RUNLQJZLWK'DWDEDVHVµ

PROGRAMMER’S GUIDE 11
CHAPTER 2 APPLICATION REQUIREMENTS

SQL statements
$Q64/DSSOLFDWLRQFRQVLVWVRIDSURJUDPZULWWHQLQDKRVWODQJXDJHOLNH&RU&LQWR
ZKLFK64/DQGG\QDPLF64/ '64/ VWDWHPHQWVDUHHPEHGGHG$Q\64/RU'64/
VWDWHPHQWVXSSRUWHGE\,QWHU%DVHFDQEHHPEHGGHGLQDKRVWODQJXDJH(DFK64/RU'64/
VWDWHPHQWPXVWEH
g 3UHFHGHGE\WKHNH\ZRUGV(;(&64/
g (QGHGZLWKWKHVWDWHPHQWWHUPLQDWRUH[SHFWHGE\WKHKRVWODQJXDJH)RUH[DPSOHLQ&DQG
&WKHKRVWWHUPLQDWRULVWKHVHPLFRORQ  
)RUDFRPSOHWHOLVWRI64/DQG'64/VWDWHPHQWVVXSSRUWHGE\,QWHU%DVHVHHWKH/DQJXDJH
5HIHUHQFH

Error handling and recovery


(YHU\WLPHDQ64/VWDWHPHQWLVH[HFXWHGLWUHWXUQVDQHUURUFRGHLQWKH64/&2'(YDULDEOH
64/&2'(LVGHFODUHGDXWRPDWLFDOO\IRU64/SURJUDPVGXULQJSUHSURFHVVLQJZLWKgpre7R
FDWFKUXQWLPHHUURUVDQGUHFRYHUIURPWKHPZKHQSRVVLEOH64/&2'(VKRXOGEHH[DPLQHG
DIWHUHDFK64/RSHUDWLRQ
64/SURYLGHVWKH:+(1(9(5VWDWHPHQWWRPRQLWRU64/&2'(DQGGLUHFWSURJUDPIORZWR
UHFRYHU\SURFHGXUHV$OWHUQDWLYHO\64/&2'(FDQEHWHVWHGGLUHFWO\DIWHUHDFK64/VWDWHPHQW
H[HFXWHV)RUDFRPSOHWHGLVFXVVLRQRI64/HUURUKDQGOLQJDQGUHFRYHU\VHH&KDSWHU
´(UURU+DQGOLQJDQG5HFRYHU\µ

Closing transactions
(YHU\WUDQVDFWLRQVKRXOGEHFORVHGZKHQLWFRPSOHWHVLWVWDVNVRUZKHQDQHUURURFFXUVWKDW
SUHYHQWVLWIURPFRPSOHWLQJLWVWDVNV)DLOXUHWRFORVHDWUDQVDFWLRQEHIRUHDSURJUDPHQGV
FDQFDXVHOLPERWUDQVDFWLRQVZKHUHUHFRUGVDUHHQWHUHGLQWRWKHGDWDEDVHEXWDUHQHLWKHU
FRPPLWWHGRUUROOHGEDFN/LPERWUDQVDFWLRQVFDQEHFOHDQHGXSXVLQJWKHGDWDEDVH
DGPLQLVWUDWLRQWRROVSURYLGHGZLWK,QWHU%DVH

12 INTERBASE 5
CLOSING TRANSACTIONS

Accepting changes
7KH&200,7VWDWHPHQWHQGVDWUDQVDFWLRQPDNHVWKHWUDQVDFWLRQ·VFKDQJHVDYDLODEOHWRRWKHU
XVHUVDQGFORVHVFXUVRUV$&200,7LVXVHGWRSUHVHUYHFKDQJHVZKHQDOORIDWUDQVDFWLRQ·V
RSHUDWLRQVDUHVXFFHVVIXO7RHQGDWUDQVDFWLRQZLWK&200,7XVHWKHIROORZLQJV\QWD[
EXEC SQL
COMMIT TRANSACTION name;

)RUH[DPSOHWKHIROORZLQJVWDWHPHQWFRPPLWVDWUDQVDFWLRQQDPHG0<75$16
EXEC SQL
COMMIT TRANSACTION MYTRANS;

)RUDFRPSOHWHGLVFXVVLRQRI64/WUDQVDFWLRQFRQWUROVHH&KDSWHU´:RUNLQJZLWK
7UDQVDFWLRQVµ

Undoing changes
7KH52//%$&.VWDWHPHQWXQGRHVDWUDQVDFWLRQ·VFKDQJHVHQGVWKHFXUUHQWWUDQVDFWLRQDQG
FORVHVRSHQFXUVRUV8VH52//%$&.ZKHQDQHUURURFFXUVWKDWSUHYHQWVDOORIDWUDQVDFWLRQ·V
RSHUDWLRQVIURPEHLQJVXFFHVVIXO7RHQGDWUDQVDFWLRQZLWK52//%$&.XVHWKHIROORZLQJ
V\QWD[
EXEC SQL
ROLLBACK TRANSACTION name;

)RUH[DPSOHWKHIROORZLQJVWDWHPHQWUROOVEDFNDWUDQVDFWLRQQDPHG0<75$16
EXEC SQL
ROLLBACK TRANSACTION MYTRANS;

7RUROOEDFNDQXQQDPHGWUDQVDFWLRQ LHWKHGHIDXOWWUDQVDFWLRQ XVHWKHIROORZLQJ


VWDWHPHQW
EXEC SQL
ROLLBACK;

)RUDFRPSOHWHGLVFXVVLRQRI64/WUDQVDFWLRQFRQWUROVHH&KDSWHU´:RUNLQJZLWK
7UDQVDFWLRQVµ

PROGRAMMER’S GUIDE 13
CHAPTER 2 APPLICATION REQUIREMENTS

Closing databases
2QFHDGDWDEDVHLVQRORQJHUQHHGHGFORVHLWEHIRUHWKHSURJUDPHQGVRUVXEVHTXHQW
DWWHPSWVWRXVHWKHGDWDEDVHPD\IDLORUUHVXOWLQGDWDEDVHFRUUXSWLRQ7KHUHDUHWZRZD\VWR
FORVHDGDWDEDVH
g 8VHWKH',6&211(&7VWDWHPHQWWRGHWDFKDGDWDEDVHDQGFORVHILOHV
g 8VHWKH5(/($6(RSWLRQZLWK&200,7RU52//%$&.LQDSURJUDP
',6&211(&7&200,75(/($6(DQG52//%$&.5(/($6(SHUIRUPWKHIROORZLQJWDVNV
g &ORVHRSHQGDWDEDVHILOHV
g &ORVHUHPRWHGDWDEDVHFRQQHFWLRQV
g 5HOHDVHWKHPHPRU\WKDWKROGVGDWDEDVHGHVFULSWLRQVDQG,QWHU%DVHHQJLQHFRPSLOHG
UHTXHVWV
Note &ORVLQJGDWDEDVHVZLWK',6&211(&7LVSUHIHUUHGIRUFRPSDWLELOLW\ZLWKWKH64/
VWDQGDUG
)RUDFRPSOHWHGLVFXVVLRQRIFORVLQJGDWDEDVHVVHH&KDSWHU´:RUNLQJZLWK'DWDEDVHVµ

DSQL requirements
'64/DSSOLFDWLRQVPXVWDGKHUHWRDOOWKHUHTXLUHPHQWVIRUDOO64/DSSOLFDWLRQVDQGPHHW
DGGLWLRQDOUHTXLUHPHQWVDVZHOO'64/DSSOLFDWLRQVHQDEOHXVHUVWRHQWHUDGKRF64/
VWDWHPHQWVIRUSURFHVVLQJDWUXQWLPH7RKDQGOHWKHZLGHYDULHW\RIVWDWHPHQWVDXVHUPLJKW
HQWHU'64/DSSOLFDWLRQVUHTXLUHWKHIROORZLQJDGGLWLRQDOSURJUDPPLQJVWHSV
g 'HFODUHDVPDQ\H[WHQGHG64/GHVFULSWRUDUHDV ;64/'$V DVDUHQHHGHGLQWKHDSSOLFDWLRQ
W\SLFDOO\DSURJUDPPXVWXVHRQHRUWZRRIWKHVHVWUXFWXUHV&RPSOH[DSSOLFDWLRQVPD\
UHTXLUHPRUH
g 'HFODUHDOOWUDQVDFWLRQQDPHVDQGGDWDEDVHKDQGOHVXVHGLQWKHSURJUDPDWFRPSLOHWLPH
QDPHVDQGKDQGOHVDUHQRWG\QDPLFVRHQRXJKPXVWEHGHFODUHGWRDFFRPPRGDWHWKH
DQWLFLSDWHGQHHGVRIXVHUVDWUXQWLPH
g 3URYLGHDPHFKDQLVPWRJHW64/VWDWHPHQWVIURPDXVHU
g 3UHSDUHHDFK64/VWDWHPHQWUHFHLYHGIURPDXVHUIRUSURFHVVLQJ
35(3$5(ORDGVVWDWHPHQWLQIRUPDWLRQLQWRWKH;64/'$
g (;(&87(HDFKSUHSDUHGVWDWHPHQW
(;(&87(,00(',$7(FRPELQHV35(3$5(DQG(;(&87(LQDVLQJOHVWDWHPHQW)RUPRUH
LQIRUPDWLRQVHHWKH/DQJXDJH5HIHUHQFH

14 INTERBASE 5
DSQL REQUIREMENTS

,QDGGLWLRQWKHV\QWD[IRUFXUVRUVLQYROYLQJ%OREGDWDGLIIHUVIURPWKDWRIFXUVRUVIRURWKHU
GDWDW\SHV)RUPRUHLQIRUPDWLRQDERXW%OREFXUVRUVWDWHPHQWVVHHWKH/DQJXDJH5HIHUHQFH

Declaring an XSQLDA
7KHH[WHQGHG64/GHVFULSWRUDUHD ;64/'$ LVXVHGDVDQLQWHUPHGLDWHVWDJLQJDUHDIRU
LQIRUPDWLRQSDVVHGEHWZHHQDQDSSOLFDWLRQDQGWKH,QWHU%DVHHQJLQH7KH;64/'$LVXVHG
IRUHLWKHURIWKHIROORZLQJWDVNV
g 3DVVLQSXWSDUDPHWHUVIURPDKRVWODQJXDJHSURJUDPWR64/
g 3DVVRXWSXWIURPD6(/(&7VWDWHPHQWRUVWRUHGSURFHGXUHIURP64/WRWKHKRVWODQJXDJH
SURJUDP
$VLQJOH;64/'$FDQEHXVHGIRURQO\RQHRIWKHVHWDVNVDWDWLPH0DQ\DSSOLFDWLRQVGHFODUH
WZR;64/'$VRQHIRULQSXWDQGDQRWKHUIRURXWSXW
7KH;64/'$VWUXFWXUHLVGHILQHGLQWKH,QWHU%DVHKHDGHUILOHLEDVHKWKDWLVDXWRPDWLFDOO\
LQFOXGHGLQSURJUDPVZKHQWKH\DUHSUHSURFHVVHGZLWKgpre
Note '64/DSSOLFDWLRQVZULWWHQXVLQJYHUVLRQVRI,QWHU%DVHSULRUWRXVHDQROGHU64/
GHVFULSWRUDUHDWKH64/'$)RUEDFNZDUGFRPSDWLELOLW\WKH64/'$FRQWLQXHVWREH
VXSSRUWHG<RXFDQH[DPLQHLWVVWUXFWXUHLQLEDVHK7KHQHZVWUXFWXUH;64/'$LVXVHG
DXWRPDWLFDOO\ZKHQSUHSURFHVVLQJDQDSSOLFDWLRQZLWKgpre7RXVHWKHROGVWUXFWXUHVSHFLI\
WKHgpreVTOGDROGVZLWFK$VFRQYHQLHQWROGHUDSSOLFDWLRQVVKRXOGEHPRGLILHGWRXVHWKH
;64/'$
7RFUHDWHDQ;64/'$IRUDSURJUDPDKRVWODQJXDJHGDWDW\SHRIWKHDSSURSULDWHW\SHPXVW
EHVHWXSLQDVHFWLRQGHFODUDWLRQ)RUH[DPSOHWKHIROORZLQJVWDWHPHQWFUHDWHVWZR;64/'$
VWUXFWXUHVLQ[VTOGDDQGRXW[VTOGD
. . .
EXEC SQL
BEGIN DECLARE SECTION;
XSQLDA inxsqlda;
XSQLDA outxsqlda;
. . .
EXEC SQL
END DECLARE SECTION;
. . .

:KHQDQDSSOLFDWLRQFRQWDLQLQJ;64/'$GHFODUDWLRQVLVSUHSURFHVVHGgpreDXWRPDWLFDOO\
LQFOXGHVWKHKHDGHUILOHLEDVHKZKLFKGHILQHVWKH;64/'$DVDKRVWODQJXDJHGDWDW\SH)RUD
FRPSOHWHGLVFXVVLRQRIWKHVWUXFWXUHRIWKH;64/'$VHH&KDSWHU´8VLQJ'\QDPLF64/µ

PROGRAMMER’S GUIDE 15
CHAPTER 2 APPLICATION REQUIREMENTS

DSQL limitations
'64/HQDEOHVSURJUDPPHUVWRFUHDWHIOH[LEOHDSSOLFDWLRQVWKDWDUHFDSDEOHRIKDQGOLQJD
ZLGHYDULHW\RIXVHUUHTXHVWV(YHQVRQRWHYHU\64/VWDWHPHQWFDQEHKDQGOHGLQD
FRPSOHWHO\G\QDPLFIDVKLRQ)RUH[DPSOHGDWDEDVHKDQGOHVDQGWUDQVDFWLRQQDPHVPXVWEH
VSHFLILHGZKHQDQDSSOLFDWLRQLVZULWWHQDQGFDQQRWEHFKDQJHGRUVSHFLILHGE\XVHUVDWUXQ
WLPH6LPLODUO\ZKLOH,QWHU%DVHVXSSRUWVPXOWLSOHGDWDEDVHVDQGPXOWLSOHVLPXOWDQHRXV
WUDQVDFWLRQVLQDQDSSOLFDWLRQWKHIROORZLQJOLPLWDWLRQVDSSO\
g 2QO\DVLQJOHGDWDEDVHFDQEHDFFHVVHGDWDWLPH
g 7UDQVDFWLRQVFDQRQO\RSHUDWHRQWKHFXUUHQWO\DFWLYHGDWDEDVH
g 8VHUVFDQQRWVSHFLI\WUDQVDFWLRQQDPHVLQ'64/VWDWHPHQWVLQVWHDGWUDQVDFWLRQQDPHV
PXVWEHVXSSOLHGDQGPDQLSXODWHGZKHQDQDSSOLFDWLRQLVFRGHG

Using database handles


'DWDEDVHKDQGOHVDUHDOZD\VVWDWLFDQGFDQRQO\EHGHFODUHGZKHQDQDSSOLFDWLRQLVFRGHG
(QRXJKKDQGOHVPXVWEHGHFODUHGWRVDWLVI\WKHH[SHFWHGQHHGVRIXVHUV2QFHDKDQGOHLV
GHFODUHGLWFDQEHDVVLJQHGWRDXVHUVSHFLILHGGDWDEDVHDWUXQWLPHZLWK6(7'$7$%$6(DV
LQWKHIROORZLQJ&FRGHIUDJPHQW
. . .
EXEC SQL
SET DATABASE DB1 = "dummydb.gdb";
EXEC SQL
SET DATABASE DB2 = "dummydb.gdb";
. . .
printf("Specify first database to open: ");
gets(fname1);
printf("\nSpecify second database to open: ");
gets(fname2);
EXEC SQL
SET DATABASE DB1 = :fname1;
EXEC SQL
SET DATABASE DB2 = :fname2;
. . .

)RUDFRPSOHWHGLVFXVVLRQRI6(7'$7$%$6(VHH&KDSWHU´:RUNLQJZLWK'DWDEDVHVµ

16 INTERBASE 5
DSQL LIMITATIONS

Using the active database


$'64/DSSOLFDWLRQFDQRQO\ZRUNZLWKRQHGDWDEDVHDWDWLPHHYHQLIWKHDSSOLFDWLRQ
DWWDFKHVWRPXOWLSOHGDWDEDVHV$OO'64/VWDWHPHQWVRSHUDWHRQO\RQWKHFXUUHQWO\DFWLYH
GDWDEDVHWKHODVWGDWDEDVHDVVRFLDWHGZLWKDKDQGOHLQD6(7'$7$%$6(VWDWHPHQW
(PEHGGHG64/VWDWHPHQWVZLWKLQD'64/DSSOLFDWLRQFDQRSHUDWHRQDQ\RSHQGDWDEDVH
)RUH[DPSOHDOO'64/VWDWHPHQWVHQWHUHGE\DXVHUDWUXQWLPHPLJKWRSHUDWHDJDLQVWDVLQJOH
GDWDEDVHVSHFLILHGE\WKHXVHUEXWWKHDSSOLFDWLRQPLJKWDOVRFRQWDLQQRQ'64/VWDWHPHQWV
WKDWUHFRUGXVHUHQWULHVLQDORJGDWDEDVH
)RUDFRPSOHWHGLVFXVVLRQRI6(7'$7$%$6(VHH&KDSWHU´:RUNLQJZLWK'DWDEDVHVµ

Using transaction names


0DQ\64/VWDWHPHQWVVXSSRUWDQRSWLRQDOWUDQVDFWLRQQDPHSDUDPHWHUXVHGWRVSHFLI\WKH
FRQWUROOLQJWUDQVDFWLRQIRUDVSHFLILFVWDWHPHQW7UDQVDFWLRQQDPHVFDQEHXVHGLQ'64/
DSSOLFDWLRQVWRREXWPXVWEHVHWXSZKHQDQDSSOLFDWLRQLVFRPSLOHG2QFHDQDPHLV
GHFODUHGLWFDQEHGLUHFWO\LQVHUWHGLQWRDXVHUVWDWHPHQWRQO\E\WKHDSSOLFDWLRQLWVHOI
$IWHUGHFODUDWLRQXVHDWUDQVDFWLRQQDPHLQDQ(;(&87(RU(;(&87(,00(',$7(
VWDWHPHQWWRVSHFLI\WKHFRQWUROOLQJWUDQVDFWLRQDVLQWKHIROORZLQJ&FRGHIUDJPHQW
. . .
EXEC SQL
BEGIN DECLARE SECTION:
long first, second; /* declare transaction names */
EXEC SQL
END DECLARE SECTION;
. . .
first = second = 0L; /* initialize names to zero */
. . .
EXEC SQL
SET TRANSACTION first; /* start transaction 1 */
EXEC SQL
SET TRANSACTION second; /* start transaction 2 */
printf("\nSQL> ");
gets(userstatement);
EXEC SQL
EXECUTE IMMEDIATE TRANSACTION first userstatement;
. . .

PROGRAMMER’S GUIDE 17
CHAPTER 2 APPLICATION REQUIREMENTS

)RUFRPSOHWHLQIRUPDWLRQDERXWQDPHGWUDQVDFWLRQVVHH&KDSWHU´:RUNLQJZLWK
7UDQVDFWLRQVµ

Preprocessing programs
$IWHUDQ64/RU'64/SURJUDPLVZULWWHQDQGEHIRUHLWLVFRPSLOHGDQGOLQNHGLWPXVWEH
SUHSURFHVVHGZLWKgpreWKH,QWHU%DVHSUHSURFHVVRUgpreWUDQVODWHV64/VWDWHPHQWVDQG
YDULDEOHVLQWRVWDWHPHQWVDQGYDULDEOHVWKDWWKHKRVWODQJXDJHFRPSLOHUDFFHSWV)RUFRPSOHWH
LQIRUPDWLRQDERXWSUHSURFHVVLQJZLWKgpreVHH&KDSWHU´3UHSURFHVVLQJ&RPSLOLQJ
DQG /LQNLQJµ

18 INTERBASE 5
CHAPTER

Working with Databases


Chapter3
3
7KLVFKDSWHUGHVFULEHVKRZWRXVH64/VWDWHPHQWVLQHPEHGGHGDSSOLFDWLRQVWRFRQWURO
GDWDEDVHV7KHUHDUHWKUHHGDWDEDVHVWDWHPHQWVWKDWVHWXSDQGRSHQGDWDEDVHVIRUDFFHVV
g 6(7'$7$%$6(GHFODUHVDGDWDEDVHKDQGOHDVVRFLDWHVWKHKDQGOHZLWKDQDFWXDOGDWDEDVHILOH
DQGRSWLRQDOO\DVVLJQVRSHUDWLRQDOSDUDPHWHUVIRUWKHGDWDEDVH
g 6(71$0(6RSWLRQDOO\VSHFLILHVWKHFKDUDFWHUVHWDFOLHQWDSSOLFDWLRQXVHVIRU&+$5
9$5&+$5DQGWH[W%OREGDWD7KHVHUYHUXVHVWKLVLQIRUPDWLRQWRWUDQVOLWHUDWHIURPD
GDWDEDVH·VGHIDXOWFKDUDFWHUVHWWRWKHFOLHQW·VFKDUDFWHUVHWRQ6(/(&7RSHUDWLRQVDQGWR
WUDQVOLWHUDWHIURPDFOLHQWDSSOLFDWLRQ·VFKDUDFWHUVHWWRWKHGDWDEDVHFKDUDFWHUVHWRQ,16(57
DQG83'$7(RSHUDWLRQV
g &211(&7RSHQVDGDWDEDVHDOORFDWHVV\VWHPUHVRXUFHVIRULWDQGRSWLRQDOO\DVVLJQV
RSHUDWLRQDOSDUDPHWHUVIRUWKHGDWDEDVH
$OOGDWDEDVHVPXVWEHFORVHGEHIRUHDSURJUDPHQGV$GDWDEDVHFDQEHFORVHGE\XVLQJ
',6&211(&7RUE\DSSHQGLQJWKH5(/($6(RSWLRQWRWKHILQDO&200,7RU52//%$&.LQ
DSURJUDP

Declaring a database
%HIRUHDGDWDEDVHFDQEHRSHQHGDQGXVHGLQDSURJUDPLWPXVWILUVWEHGHFODUHGZLWK6(7
'$7$%$6(WR

19
CHAPTER 3 WORKING WITH DATABASES

g (VWDEOLVKDGDWDEDVHKDQGOH
g $VVRFLDWHWKHGDWDEDVHKDQGOHZLWKDGDWDEDVHILOHVWRUHGRQDORFDORUUHPRWHQRGH
$GDWDEDVHKDQGOHLVDXQLTXHDEEUHYLDWHGDOLDVIRUDQDFWXDOGDWDEDVHQDPH'DWDEDVHKDQGOHV
DUHXVHGLQVXEVHTXHQW&211(&7&200,75(/($6(DQG52//%$&.5(/($6(VWDWHPHQWV
WRVSHFLI\ZKLFKGDWDEDVHVWKH\VKRXOGDIIHFW([FHSWLQG\QDPLF64/ '64/ DSSOLFDWLRQV
GDWDEDVHKDQGOHVFDQDOVREHXVHGLQVLGHWUDQVDFWLRQEORFNVWRTXDOLI\RUGLIIHUHQWLDWHWDEOH
QDPHVZKHQWZRRUPRUHRSHQGDWDEDVHVFRQWDLQLGHQWLFDOO\QDPHGWDEOHV
(DFKGDWDEDVHKDQGOHPXVWEHXQLTXHDPRQJDOOYDULDEOHVXVHGLQDSURJUDP'DWDEDVH
KDQGOHVFDQQRWGXSOLFDWHKRVWODQJXDJHUHVHUYHGZRUGVDQGFDQQRWEH,QWHU%DVHUHVHUYHG
ZRUGV
7KHIROORZLQJVWDWHPHQWLOOXVWUDWHVDVLPSOHGDWDEDVHGHFODUDWLRQ
EXEC SQL
SET DATABASE DB1 = "employee.gdb";

7KLVGDWDEDVHGHFODUDWLRQLGHQWLILHVWKHGDWDEDVHILOHHPSOR\HHJGEDVDGDWDEDVHWKHSURJUDP
XVHVDQGDVVLJQVWKHGDWDEDVHDKDQGOHRUDOLDV'%
,IDSURJUDPUXQVLQDGLUHFWRU\GLIIHUHQWIURPWKHGLUHFWRU\WKDWFRQWDLQVWKHGDWDEDVHILOH
WKHQWKHILOHQDPHVSHFLILFDWLRQLQ6(7'$7$%$6(PXVWLQFOXGHDIXOOSDWKQDPHWRR)RU
H[DPSOHWKHIROORZLQJ6(7'$7$%$6(GHFODUDWLRQVSHFLILHVWKHIXOOSDWKWRHPSOR\HHJGE
EXEC SQL
SET DATABASE DB1 = "/interbase/examples/employee.gdb";

,IDSURJUDPDQGDGDWDEDVHILOHLWXVHVUHVLGHRQGLIIHUHQWKRVWVWKHQWKHILOHQDPH
VSHFLILFDWLRQPXVWDOVRLQFOXGHDKRVWQDPH7KHIROORZLQJGHFODUDWLRQLOOXVWUDWHVKRZD8QL[
KRVWQDPHLVLQFOXGHGDVSDUWRIWKHGDWDEDVHILOHVSHFLILFDWLRQRQD7&3,3QHWZRUN
EXEC SQL
SET DATABASE DB1 = "jupiter:/usr/interbase/examples/employee.gdb";

2QD:LQGRZVQHWZRUNWKDWXVHVWKH1HWEHXLSURWRFROVSHFLI\WKHSDWKDVIROORZV
EXEC SQL
SET DATABASE DB1 = "//venus/C:/Interbase/examples/employee.gdb";

Declaring multiple databases


$Q64/SURJUDPEXWQRWD'64/SURJUDPFDQDFFHVVPXOWLSOHGDWDEDVHVDWWKHVDPHWLPH
,QPXOWLGDWDEDVHSURJUDPVGDWDEDVHKDQGOHVDUHUHTXLUHG$KDQGOHLVXVHGWR
g 5HIHUHQFHLQGLYLGXDOGDWDEDVHVLQDPXOWLGDWDEDVHWUDQVDFWLRQ
g 4XDOLI\WDEOHQDPHV

20 INTERBASE 5
DECLARING A DATABASE

g 6SHFLI\GDWDEDVHVWRRSHQLQ&211(&7VWDWHPHQWV
g ,QGLFDWHGDWDEDVHVWRFORVHZLWK',6&211(&7&200,75(/($6(DQG52//%$&.
5(/($6(
'64/SURJUDPVFDQDFFHVVRQO\DVLQJOHGDWDEDVHDWDWLPHVRGDWDEDVHKDQGOHXVHLV
UHVWULFWHGWRFRQQHFWLQJWRDQGGLVFRQQHFWLQJIURPDGDWDEDVH
,QPXOWLGDWDEDVHSURJUDPVHDFKGDWDEDVHPXVWEHGHFODUHGLQDVHSDUDWH6(7'$7$%$6(
VWDWHPHQW)RUH[DPSOHWKHIROORZLQJFRGHFRQWDLQVWZR6(7'$7$%$6(VWDWHPHQWV
. . .
EXEC SQL
SET DATABASE DB2 = "employee2.gdb";
EXEC SQL
SET DATABASE DB1 = "employee.gdb";
. . .

4 8VLQJKDQGOHVIRUWDEOHQDPHV
:KHQWKHVDPHWDEOHQDPHRFFXUVLQPRUHWKDQRQHVLPXOWDQHRXVO\DFFHVVHGGDWDEDVHD
GDWDEDVHKDQGOHPXVWEHXVHGWRGLIIHUHQWLDWHRQHWDEOHQDPHIURPDQRWKHU7KHGDWDEDVH
KDQGOHLVXVHGDVDSUHIL[WRWDEOHQDPHVDQGWDNHVWKHIRUPKDQGOHWDEOH
)RUH[DPSOHLQWKHIROORZLQJFRGHWKHGDWDEDVHKDQGOHV7(67DQG(03DUHXVHGWR
GLVWLQJXLVKEHWZHHQWZRWDEOHVHDFKQDPHG(03/2<((
. . .
EXEC SQL
DECLARE IDMATCH CURSOR FOR
SELECT TESTNO INTO :matchid FROM TEST.EMPLOYEE
WHERE TESTNO > 100;
EXEC SQL
DECLARE EIDMATCH CURSOR FOR
SELECT EMPNO INTO :empid FROM EMP.EMPLOYEE
WHERE EMPNO = :matchid;
. . .

,03257$17 7KLVXVHRIGDWDEDVHKDQGOHVDSSOLHVRQO\WRHPEHGGHG64/DSSOLFDWLRQV'64/
DSSOLFDWLRQVFDQQRWDFFHVVPXOWLSOHGDWDEDVHVVLPXOWDQHRXVO\

4 8VLQJKDQGOHVZLWKRSHUDWLRQV
,QPXOWLGDWDEDVHSURJUDPVGDWDEDVHKDQGOHVPXVWEHVSHFLILHGLQ&211(&7VWDWHPHQWVWR
LGHQWLI\ZKLFKGDWDEDVHVDPRQJVHYHUDOWRRSHQDQGSUHSDUHIRUXVHLQVXEVHTXHQW
WUDQVDFWLRQV

PROGRAMMER’S GUIDE 21
CHAPTER 3 WORKING WITH DATABASES

'DWDEDVHKDQGOHVFDQDOVREHXVHGZLWK',6&211(&7&200,75(/($6(DQG52//%$&.
5(/($6(WRVSHFLI\DVXEVHWRIRSHQGDWDEDVHVWRFORVH
7RRSHQDQGSUHSDUHDGDWDEDVHZLWK&211(&7VHH´2SHQLQJDGDWDEDVHµRQSDJH 7R
FORVHDGDWDEDVHZLWK',6&211(&7&200,75(/($6(RU52//%$&.5(/($6(VHH
´&ORVLQJDGDWDEDVHµRQSDJH 7ROHDUQPRUHDERXWXVLQJGDWDEDVHKDQGOHVLQWUDQVDFWLRQV
VHH´$FFHVVLQJDQRSHQGDWDEDVHµRQSDJH 

Preprocessing and run time databases


1RUPDOO\HDFK6(7'$7$%$6(VWDWHPHQWVSHFLILHVDVLQJOHGDWDEDVHILOHWRDVVRFLDWHZLWKD
KDQGOH:KHQDSURJUDPLVSUHSURFHVVHGgpreXVHVWKHVSHFLILHGILOHWRYDOLGDWHWKH
SURJUDP·VWDEOHDQGFROXPQUHIHUHQFHV/DWHUZKHQDXVHUUXQVWKHSURJUDPWKHVDPH
GDWDEDVHILOHLVDFFHVVHG'LIIHUHQWGDWDEDVHVFDQEHVSHFLILHGIRUSUHSURFHVVLQJDQGUXQWLPH
ZKHQQHFHVVDU\

4 8VLQJWKH&203,/(7,0(FODXVH
$SURJUDPFDQEHGHVLJQHGWRUXQDJDLQVWDQ\RQHRIVHYHUDOLGHQWLFDOO\VWUXFWXUHGGDWDEDVHV
,QRWKHUFDVHVWKHDFWXDOGDWDEDVHWKDWDSURJUDPZLOOXVHDWUXQWLPHLVQRWDYDLODEOHZKHQD
SURJUDPLVSUHSURFHVVHGDQGFRPSLOHG,QVXFKFDVHV6(7'$7$%$6(FDQLQFOXGHD
&203,/(7,0(FODXVHWRVSHFLI\DGDWDEDVHIRUgpreWRWHVWDJDLQVWGXULQJSUHSURFHVVLQJ)RU
H[DPSOHWKHIROORZLQJ6(7'$7$%$6(VWDWHPHQWGHFODUHVWKDWHPSOR\HHJGELVWREHXVHGE\
gpreGXULQJSUHSURFHVVLQJ
EXEC SQL
SET DATABASE EMP = COMPILETIME "employee.gdb";

,03257$17 7KHILOHVSHFLILFDWLRQWKDWIROORZVWKH&203,/(7,0(NH\ZRUGPXVWDOZD\VEHDKDUGFRGHG
TXRWHGVWULQJ
:KHQ6(7'$7$%$6(XVHVWKH&203,/(7,0(FODXVHEXWQR5817,0(FODXVHDQGGRHVQRW
VSHFLI\DGLIIHUHQWGDWDEDVHILOHVSHFLILFDWLRQLQDVXEVHTXHQW&211(&7VWDWHPHQWWKHVDPH
GDWDEDVHILOHLVXVHGERWKIRUSUHSURFHVVLQJDQGUXQWLPH7RVSHFLI\GLIIHUHQWSUHSURFHVVLQJ
DQGUXQWLPHGDWDEDVHVZLWK6(7'$7$%$6(XVHERWKWKH&203,/(7,0(DQG5817,0(
FODXVHV

4 8VLQJWKH5817,0(FODXVH
:KHQDGDWDEDVHILOHLVVSHFLILHGIRUXVHGXULQJSUHSURFHVVLQJ6(7'$7$%$6(FDQVSHFLI\D
GLIIHUHQWGDWDEDVHWRXVHDWUXQWLPHE\LQFOXGLQJWKH5817,0(NH\ZRUGDQGDUXQWLPHILOH
VSHFLILFDWLRQ

22 INTERBASE 5
DECLARING A DATABASE

EXEC SQL
SET DATABASE EMP = COMPILETIME "employee.gdb"
RUNTIME "employee2.gdb";

7KHILOHVSHFLILFDWLRQWKDWIROORZVWKH5817,0(NH\ZRUGFDQEHHLWKHUDKDUGFRGHGTXRWHG
VWULQJRUDKRVWODQJXDJHYDULDEOH)RUH[DPSOHWKHIROORZLQJ&FRGHIUDJPHQWSURPSWVWKH
XVHUIRUDGDWDEDVHQDPHDQGVWRUHVWKHQDPHLQDYDULDEOHWKDWLVXVHGODWHULQ6(7
'$7$%$6(
. . .
char db_name[125];
. . .
printf("Enter the desired database name, including node and path):\n");
gets(db_name);
EXEC SQL
SET DATABASE EMP = COMPILETIME "employee.gdb" RUNTIME :db_name;
. . .
Note +RVWODQJXDJHYDULDEOHVLQ6(7'$7$%$6(PXVWEHSUHFHGHGDVDOZD\VE\DFRORQ

Controlling SET DATABASE scope


%\GHIDXOW6(7'$7$%$6(FUHDWHVDKDQGOHWKDWLVJOREDOWRDOOPRGXOHVLQDQDSSOLFDWLRQ$
JOREDOKDQGOHLVRQHWKDWPD\EHUHIHUHQFHGLQDOOKRVWODQJXDJHPRGXOHVFRPSULVLQJWKH
SURJUDP6(7'$7$%$6(SURYLGHVWZRRSWLRQDONH\ZRUGVWRFKDQJHWKHVFRSHRID
GHFODUDWLRQ
g 67$7,&OLPLWVGHFODUDWLRQVFRSHWRWKHPRGXOHFRQWDLQLQJWKH6(7'$7$%$6(VWDWHPHQW1R
RWKHUSURJUDPPRGXOHVFDQVHHRUXVHDGDWDEDVHKDQGOHGHFODUHG67$7,&
g (;7(51QRWLILHVgpreWKDWD6(7'$7$%$6(VWDWHPHQWLQDPRGXOHGXSOLFDWHVD
JOREDOO\GHFODUHGGDWDEDVHLQDQRWKHUPRGXOH,IWKH(;7(51NH\ZRUGLVXVHGWKHQDQRWKHU
PRGXOHPXVWFRQWDLQWKHDFWXDO6(7'$7$%$6(VWDWHPHQWRUDQHUURURFFXUVGXULQJ
FRPSLODWLRQ
7KH67$7,&NH\ZRUGLVXVHGLQDPXOWLPRGXOHSURJUDPWRUHVWULFWGDWDEDVHKDQGOHDFFHVVWR
WKHVLQJOHPRGXOHZKHUHLWLVGHFODUHG7KHIROORZLQJH[DPSOHLOOXVWUDWHVWKHXVHRIWKH
67$7,&NH\ZRUG
EXEC SQL
SET DATABASE EMP = STATIC "employee.gdb";

7KH(;7(51NH\ZRUGLVXVHGLQDPXOWLPRGXOHSURJUDPWRVLJQDOWKDW6(7'$7$%$6(LQ
RQHPRGXOHLVQRWDQDFWXDOGHFODUDWLRQEXWUHIHUVWRDGHFODUDWLRQPDGHLQDGLIIHUHQW
PRGXOHgpreXVHVWKLVLQIRUPDWLRQGXULQJSUHSURFHVVLQJ7KHIROORZLQJH[DPSOHLOOXVWUDWHV
WKHXVHRIWKH(;7(51NH\ZRUG

PROGRAMMER’S GUIDE 23
CHAPTER 3 WORKING WITH DATABASES

EXEC SQL
SET DATABASE EMP = EXTERN "employee.gdb";

,IDQDSSOLFDWLRQFRQWDLQVDQ(;7(51UHIHUHQFHWKHQZKHQLWLVXVHGDWUXQWLPHWKHDFWXDO
6(7'$7$%$6(GHFODUDWLRQPXVWEHSURFHVVHGILUVWDQGWKHGDWDEDVHFRQQHFWHGEHIRUHRWKHU
PRGXOHVFDQDFFHVVLW
$VLQJOH6(7'$7$%$6(VWDWHPHQWFDQFRQWDLQHLWKHUWKH67$7,&RU(;7(51NH\ZRUGEXW
QRWERWK$VFRSHGHFODUDWLRQLQ6(7'$7$%$6(DSSOLHVWRERWK
&203,/(7,0(DQG5817,0(GDWDEDVHV

Specifying a connection character set


:KHQDFOLHQWDSSOLFDWLRQFRQQHFWVWRDGDWDEDVHLWPD\KDYHLWVRZQFKDUDFWHUVHW
UHTXLUHPHQWV7KHVHUYHUSURYLGLQJGDWDEDVHDFFHVVWRWKHFOLHQWGRHVQRWNQRZDERXWWKHVH
UHTXLUHPHQWVXQOHVVWKHFOLHQWVSHFLILHVWKHP7KHFOLHQWDSSOLFDWLRQVSHFLILHVLWVFKDUDFWHUVHW
UHTXLUHPHQWXVLQJWKH6(71$0(6VWDWHPHQWEHIRUHLWFRQQHFWVWRWKHGDWDEDVH
6(71$0(6VSHFLILHVWKHFKDUDFWHUVHWWKHVHUYHUVKRXOGXVHZKHQWUDQVODWLQJGDWDIURPWKH
GDWDEDVHWRWKHFOLHQWDSSOLFDWLRQ6LPLODUO\ZKHQWKHFOLHQWVHQGVGDWDWRWKHGDWDEDVHWKH
VHUYHUWUDQVODWHVWKHGDWDIURPWKHFOLHQW·VFKDUDFWHUVHWWRWKHGDWDEDVH·VGHIDXOWFKDUDFWHUVHW
RUWKHFKDUDFWHUVHWIRUDQLQGLYLGXDOFROXPQLILWGLIIHUVIURPWKHGDWDEDVH·VGHIDXOWFKDUDFWHU
VHW 
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVVSHFLI\WKDWWKHFOLHQWLVXVLQJWKH'26FKDUDFWHU
VHWWKHQFRQQHFWWRWKHGDWDEDVH
EXEC SQL
SET NAMES DOS437;
EXEC SQL
CONNECT "europe.gdb" USER "JAMES" PASSWORD "U4EEAH";

)RUPRUHLQIRUPDWLRQDERXWFKDUDFWHUVHWVVHHWKH'DWD'HILQLWLRQ*XLGH)RUWKHFRPSOHWH
V\QWD[RI6(71$0(6DQG&211(&7VHHWKH/DQJXDJH5HIHUHQFH

Opening a database
$IWHUDGDWDEDVHLVGHFODUHGLWPXVWEHDWWDFKHGZLWKD&211(&7VWDWHPHQWEHIRUHLWFDQEH
XVHG&211(&7
g $OORFDWHVV\VWHPUHVRXUFHVIRUWKHGDWDEDVH

24 INTERBASE 5
OPENING A DATABASE

g 'HWHUPLQHVLIWKHGDWDEDVHILOHLVORFDOUHVLGLQJRQWKHVDPHKRVWZKHUHWKHDSSOLFDWLRQLWVHOI
LVUXQQLQJRUUHPRWHUHVLGLQJRQDGLIIHUHQWKRVW
g 2SHQVWKHGDWDEDVHDQGH[DPLQHVLWWRPDNHVXUHLWLVYDOLG
,QWHU%DVHSURYLGHVWUDQVSDUHQWDFFHVVWRDOOGDWDEDVHVZKHWKHUORFDORUUHPRWH,IWKH
GDWDEDVHVWUXFWXUHLVLQYDOLGWKHRQGLVNVWUXFWXUH 2'6 QXPEHUGRHVQRWFRUUHVSRQGWRWKH
RQHUHTXLUHGE\,QWHU%DVHRULIWKHGDWDEDVHLVFRUUXSW,QWHU%DVHUHSRUWVDQHUURUDQG
SHUPLWVQRIXUWKHUDFFHVV
2SWLRQDOO\&211(&7FDQEHXVHGWRVSHFLI\
g $XVHUQDPHDQGSDVVZRUGFRPELQDWLRQWKDWLVFKHFNHGDJDLQVWWKHVHUYHU·VVHFXULW\GDWDEDVH
EHIRUHDOORZLQJWKHFRQQHFWWRVXFFHHG8VHUQDPHVFDQEHXSWRFKDUDFWHUV3DVVZRUGV
DUHUHVWULFWHGWRFKDUDFWHUV
g $Q64/UROHQDPHWKDWWKHXVHUDGRSWVRQFRQQHFWLRQWRWKHGDWDEDVHSURYLGHGWKDWWKHXVHU
KDVSUHYLRXVO\EHHQJUDQWHGPHPEHUVKLSLQWKHUROH5HJDUGOHVVRIUROHPHPEHUVKLSV
JUDQWHGWKHXVHUEHORQJVWRQRUROHXQOHVVVSHFLILHGZLWKWKLV52/(FODXVH7KHFOLHQWFDQ
VSHFLI\DWPRVWRQHUROHSHUFRQQHFWLRQDQGFDQQRWVZLWFKUROHVH[FHSWE\UHFRQQHFWLQJ
g 7KHVL]HRIWKHGDWDEDVHEXIIHUFDFKHWRDOORFDWHWRWKHDSSOLFDWLRQZKHQWKHGHIDXOWFDFKH
VL]HLVLQDSSURSULDWH

Using simple CONNECT statements


,QLWVVLPSOHVWIRUP&211(&7UHTXLUHVRQHRUPRUHGDWDEDVHSDUDPHWHUVHDFKVSHFLI\LQJ
WKHQDPHRIDGDWDEDVHWRRSHQ7KHQDPHRIWKHGDWDEDVHFDQEHD
g 'DWDEDVHKDQGOHGHFODUHGLQDSUHYLRXV6(7'$7$%$6(VWDWHPHQW
g +RVWODQJXDJHYDULDEOH
g +DUGFRGHGILOHQDPH

4 8VLQJDGDWDEDVHKDQGOH
,IDSURJUDPXVHV6(7'$7$%$6(WRSURYLGHGDWDEDVHKDQGOHVWKRVHKDQGOHVVKRXOGEHXVHG
LQVXEVHTXHQW&211(&7VWDWHPHQWVLQVWHDGRIKDUGFRGHGQDPHV)RUH[DPSOH
. . .
EXEC SQL
SET DATABASE DB1 = "employee.gdb";
EXEC SQL
SET DATABASE DB2 = "employee2.gdb";
EXEC SQL
CONNECT DB1;

PROGRAMMER’S GUIDE 25
CHAPTER 3 WORKING WITH DATABASES

EXEC SQL
CONNECT DB2;
. . .

7KHUHDUHVHYHUDODGYDQWDJHVWRXVLQJDGDWDEDVHKDQGOHZLWK&211(&7
g /RQJILOHVSHFLILFDWLRQVFDQEHUHSODFHGE\VKRUWHUPQHPRQLFKDQGOHV
g +DQGOHVFDQEHXVHGWRTXDOLI\WDEOHQDPHVLQPXOWLGDWDEDVHWUDQVDFWLRQV'64/
DSSOLFDWLRQVGRQRWVXSSRUWPXOWLGDWDEDVHWUDQVDFWLRQV
g +DQGOHVFDQEHUHDVVLJQHGWRRWKHUGDWDEDVHVDVQHHGHG
g 7KHQXPEHURIGDWDEDVHFDFKHEXIIHUVFDQEHVSHFLILHGDVDQDGGLWLRQDO&211(&7
SDUDPHWHU
)RUPRUHLQIRUPDWLRQDERXWVHWWLQJWKHQXPEHURIGDWDEDVHFDFKHEXIIHUVVHH´6HWWLQJ
GDWDEDVHFDFKHEXIIHUVµRQSDJH 

4 8VLQJVWULQJVRUKRVWODQJXDJHYDULDEOHV
,QVWHDGRIXVLQJDGDWDEDVHKDQGOH&211(&7FDQXVHDGDWDEDVHQDPHVXSSOLHGDWUXQWLPH
7KHGDWDEDVHQDPHFDQEHVXSSOLHGDVHLWKHUDKRVWODQJXDJHYDULDEOHRUDKDUGFRGHGTXRWHG
VWULQJ
7KHIROORZLQJ&FRGHGHPRQVWUDWHVKRZDSURJUDPDFFHVVLQJRQO\DVLQJOHGDWDEDVHPLJKW
LPSOHPHQW&211(&7XVLQJDILOHQDPHVROLFLWHGIURPDXVHUDWUXQWLPH
. . .
char fname[125];
. . .
printf("Enter the desired database name, including node and path):\n");
gets(fname);
. . .
EXEC SQL
CONNECT :fname;
. . .

7,3 7KLVWHFKQLTXHLVHVSHFLDOO\XVHIXOIRUSURJUDPVWKDWDUHGHVLJQHGWRZRUNZLWKPDQ\
LGHQWLFDOO\VWUXFWXUHGGDWDEDVHVRQHDWDWLPHVXFKDV&$'&$0RUDUFKLWHFWXUDO
GDWDEDVHV

MULTIPLE DATABASE IMPLEMENTATION


7RXVHDGDWDEDVHVSHFLILHGE\WKHXVHUDVDKRVWODQJXDJHYDULDEOHLQD&211(&7VWDWHPHQW
LQPXOWLGDWDEDVHSURJUDPVIROORZWKHVHVWHSV

26 INTERBASE 5
OPENING A DATABASE

 'HFODUHDGDWDEDVHKDQGOHXVLQJWKHIROORZLQJ6(7'$7$%$6(V\QWD[
EXEC SQL
SET DATABASE handle = COMPILETIME "dbname";

+HUHKDQGOHLVDKDUGFRGHGGDWDEDVHKDQGOHVXSSOLHGE\WKHSURJUDPPHUGEQDPHLVD
TXRWHGKDUGFRGHGGDWDEDVHQDPHXVHGE\gpreGXULQJSUHSURFHVVLQJ
 3URPSWWKHXVHUIRUDGDWDEDVHWRRSHQ
 6WRUHWKHGDWDEDVHQDPHHQWHUHGE\WKHXVHULQDKRVWODQJXDJHYDULDEOH
 8VHWKHKDQGOHWRRSHQWKHGDWDEDVHDVVRFLDWLQJWKHKRVWODQJXDJHYDULDEOHZLWK
WKHKDQGOHXVLQJWKHIROORZLQJ&211(&7V\QWD[
EXEC SQL
CONNECT :variable AS handle;

7KHIROORZLQJ&FRGHLOOXVWUDWHVWKHVHVWHSV
. . .
char fname[125];
. . .
EXEC SQL
SET DATABASE DB1 = "employee.gdb";
printf("Enter the desired database name, including node and path):\n");
gets(fname);
EXEC SQL
CONNECT :fname AS DB1;
. . .

,QWKLVH[DPSOH6(7'$7$%$6(SURYLGHVDKDUGFRGHGGDWDEDVHILOHQDPHIRUSUHSURFHVVLQJ
ZLWKgpre:KHQDXVHUUXQVWKHSURJUDPWKHGDWDEDVHVSHFLILHGLQWKHYDULDEOHIQDPHLVXVHG
LQVWHDG

4 8VLQJDKDUGFRGHGGDWDEDVHQDPHV
IN SINGE-DATABASE PROGRAMS
,QDVLQJOHGDWDEDVHSURJUDPWKDWRPLWV6(7'$7$%$6(&211(&7PXVWFRQWDLQD
KDUGFRGHGTXRWHGILOHQDPHLQWKHIROORZLQJIRUPDW
EXEC SQL
CONNECT "[host[path]]filename";

KRVWLVRQO\UHTXLUHGLIDSURJUDPDQGDGDWDEDVHILOHLWXVHVUHVLGHRQGLIIHUHQWQRGHV6LPLODUO\
SDWKLVRQO\UHTXLUHGLIWKHGDWDEDVHILOHGRHVQRWUHVLGHLQWKHFXUUHQWZRUNLQJGLUHFWRU\)RU
H[DPSOHWKHIROORZLQJ&211(&7VWDWHPHQWFRQWDLQVDKDUGFRGHGILOHQDPHWKDWLQFOXGHV
ERWKD8QL[KRVWQDPHDQGDSDWKQDPH

PROGRAMMER’S GUIDE 27
CHAPTER 3 WORKING WITH DATABASES

EXEC SQL
CONNECT "valdez:usr/interbase/examples/employee.gdb";
Note +RVWV\QWD[LVVSHFLILFWRHDFKVHUYHUSODWIRUP

,03257$17 $SURJUDPWKDWDFFHVVHVPXOWLSOHGDWDEDVHVFDQQRWXVHWKLVIRUPRI&211(&7

IN MULTI-DATABASE PROGRAMS
$SURJUDPWKDWDFFHVVHVPXOWLSOHGDWDEDVHVPXVWGHFODUHKDQGOHVIRUHDFKRIWKHPLQVHSDUDWH
6(7'$7$%$6(VWDWHPHQWV7KHVHKDQGOHVPXVWEHXVHGLQVXEVHTXHQW&211(&7VWDWHPHQWV
WRLGHQWLI\VSHFLILFGDWDEDVHVWRRSHQ
. . .
EXEC SQL
SET DATABASE DB1 = "employee.gdb";
EXEC SQL
SET DATABASE DB2 = "employee2.gdb";
EXEC SQL
CONNECT DB1;
EXEC SQL
CONNECT DB2;
. . .

/DWHUZKHQWKHSURJUDPFORVHVWKHVHGDWDEDVHVWKHGDWDEDVHKDQGOHVDUHQRORQJHULQXVH
7KHVHKDQGOHVFDQEHUHDVVLJQHGWRRWKHUGDWDEDVHVE\KDUGFRGLQJDILOHQDPHLQD
VXEVHTXHQW&211(&7VWDWHPHQW)RUH[DPSOH
. . .
EXEC SQL
DISCONNECT DB1, DB2;
EXEC SQL
CONNECT "project.gdb" AS DB1;
. . .

28 INTERBASE 5
OPENING A DATABASE

Additional CONNECT syntax


&211(&7VXSSRUWVVHYHUDOIRUPDWVIRURSHQLQJGDWDEDVHVWRSURYLGHSURJUDPPLQJ
IOH[LELOLW\7KHIROORZLQJWDEOHRXWOLQHVHDFKSRVVLEOHV\QWD[SURYLGHVGHVFULSWLRQVDQG
H[DPSOHVDQGLQGLFDWHVZKHWKHU&211(&7FDQEHXVHGLQSURJUDPVWKDWDFFHVVVLQJOHRU
PXOWLSOHGDWDEDVHV

Single Multiple
Syntax Description Example access access
CONNECT “dbfile”; Open a single, hard-coded database file, dbfile. EXEC SQL Yes No
CONNECT
“employee.gdb”;
CONNECT handle; Open the database file associated with a EXEC SQL Yes Yes
previously declared database handle. This is the CONNECT EMP;
preferred CONNECT syntax.
CONNECT “dbfile” AS Open a hard-coded database file, dbfile, and EXEC SQL Yes Yes
handle; assign a previously declared database handle to CONNECT
it. “employee.gdb”
AS EMP;
CONNECT :varname AS Open the database file stored in the EXEC SQL Yes Yes
handle; host-language variable, varname, and assign a CONNECT :fname AS
previously declared database handle to it. EMP;

TABLE 3.1 CONNECT syntax summary

)RUDFRPSOHWHGLVFXVVLRQRI&211(&7V\QWD[DQGLWVXVHVVHHWKH/DQJXDJH5HIHUHQFH

Attaching to multiple databases


&211(&7FDQDWWDFKWRPXOWLSOHGDWDEDVHV7RRSHQDOOGDWDEDVHVVSHFLILHGLQSUHYLRXV6(7
'$7$%$6(VWDWHPHQWVXVHHLWKHURIWKHIROORZLQJ&211(&7V\QWD[RSWLRQV
EXEC SQL
CONNECT ALL;

EXEC SQL
CONNECT DEFAULT;

PROGRAMMER’S GUIDE 29
CHAPTER 3 WORKING WITH DATABASES

&211(&7FDQDOVRDWWDFKWRDVSHFLILHGOLVWRIGDWDEDVHV6HSDUDWHHDFKGDWDEDVHUHTXHVWIURP
RWKHUVZLWKFRPPDV)RUH[DPSOHWKHIROORZLQJVWDWHPHQWRSHQVWZRGDWDEDVHVVSHFLILHGE\
WKHLUKDQGOHV
EXEC SQL
CONNECT DB1, DB2;

7KHQH[WVWDWHPHQWRSHQVWZRKDUGFRGHGGDWDEDVHILOHVDQGDOVRDVVLJQVWKHPWRSUHYLRXVO\
GHFODUHGKDQGOHV
EXEC SQL
CONNECT "employee.gdb" AS DB1, "employee2.gdb" AS DB2;

7,3 2SHQLQJPXOWLSOHGDWDEDVHVZLWKDVLQJOH&211(&7LVPRVWHIIHFWLYHZKHQDSURJUDP·V
GDWDEDVHDFFHVVLVVLPSOHDQGFOHDU,QFRPSOH[SURJUDPVWKDWRSHQDQGFORVHVHYHUDO
GDWDEDVHVWKDWVXEVWLWXWHGDWDEDVHQDPHVZLWKKRVWODQJXDJHYDULDEOHVRUWKDWDVVLJQ
PXOWLSOHKDQGOHVWRWKHVDPHGDWDEDVHXVHVHSDUDWH&211(&7VWDWHPHQWVWRPDNHSURJUDP
FRGHHDVLHUWRUHDGGHEXJDQGPRGLI\

Handling CONNECT errors


7KH:+(1(9(5VWDWHPHQWVKRXOGEHXVHGWRWUDSDQGKDQGOHUXQWLPHHUURUVWKDWRFFXU
GXULQJGDWDEDVHGHFODUDWLRQ7KHIROORZLQJ&FRGHIUDJPHQWLOOXVWUDWHVDQHUURUKDQGOLQJ
URXWLQHWKDWGLVSOD\VHUURUPHVVDJHVDQGHQGVWKHSURJUDPLQDQRUGHUO\IDVKLRQ
. . .
EXEC SQL
WHENEVER SQLERROR
GOTO error_exit;
. . .
:error_exit
isc_print_sqlerr(sqlcode, status_vector);
EXEC SQL
DISCONNECT ALL;
exit(1);
. . .

)RUDFRPSOHWHGLVFXVVLRQRI64/HUURUKDQGOLQJVHH&KDSWHU´(UURU+DQGOLQJDQG
5HFRYHU\µ

30 INTERBASE 5
OPENING A DATABASE

Setting database cache buffers


%HVLGHVRSHQLQJDGDWDEDVH&211(&7FDQVHWWKHQXPEHURIFDFKHEXIIHUVDVVLJQHGWRD
GDWDEDVHIRUWKDWFRQQHFWLRQ:KHQDSURJUDPHVWDEOLVKHVDFRQQHFWLRQWRDGDWDEDVH
,QWHU%DVHDOORFDWHVV\VWHPPHPRU\WRXVHDVDSULYDWHEXIIHU7KHEXIIHUVDUHXVHGWRVWRUH
DFFHVVHGGDWDEDVHSDJHVWRVSHHGSHUIRUPDQFH7KHQXPEHURIEXIIHUVDVVLJQHGIRUD
SURJUDPGHWHUPLQHKRZPDQ\VLPXOWDQHRXVGDWDEDVHSDJHVLWFDQKDYHDFFHVVWRLQWKH
PHPRU\SRRO%XIIHUVUHPDLQDVVLJQHGXQWLODSURJUDPILQLVKHVZLWKDGDWDEDVH
7KHGHIDXOWQXPEHURIGDWDEDVHFDFKHEXIIHUVDVVLJQHGWRDGDWDEDVHLV7KLVGHIDXOWFDQ
EHFKDQJHGHLWKHUIRUDVSHFLILFGDWDEDVHRUIRUDQHQWLUHVHUYHU
g 8VHWKHgfixXWLOLW\WRVHWDQHZGHIDXOWFDFKHEXIIHUVL]HIRUDGDWDEDVH6HHWKH2SHUDWLRQV
*XLGHIRUPRUHLQIRUPDWLRQDERXWVHWWLQJGDWDEDVHEXIIHUVL]HZLWKgfix
g &KDQJHWKHYDOXHRI'$7$%$6(B&$&+(B3$*(6LQWKH,QWHU%DVHFRQILJXUDWLRQILOHWRFKDQJH
WKHGHIDXOWFDFKHEXIIHUVL]HRQDVHUYHUZLGHEDVLV8VHWKLVRSWLRQZLWKFDUHVLQFHLWPDNHV
LWHDV\WRRYHUXVHPHPRU\RUFUHDWHXQXVDEO\VPDOOFDFKHV

4 6HWWLQJLQGLYLGXDOGDWDEDVHEXIIHUV
)RUSURJUDPVWKDWDFFHVVRUFKDQJHPDQ\URZVLQPDQ\GDWDEDVHVSHUIRUPDQFHFDQ
VRPHWLPHVEHLPSURYHGE\LQFUHDVLQJWKHQXPEHURIEXIIHUV7KHPD[LPXPQXPEHURI
EXIIHUVDOORZHGLVV\VWHPGHSHQGHQW
g 8VHWKH&$&+(QSDUDPHWHUZLWK&211(&7WRFKDQJHWKHQXPEHURIEXIIHUVDVVLJQHGWRD
GDWDEDVHIRUWKHGXUDWLRQRIWKHFRQQHFWLRQZKHUHQLVWKHQXPEHURIEXIIHUVWRUHVHUYH7R
VHWWKHQXPEHURIEXIIHUVIRUDQLQGLYLGXDOGDWDEDVHSODFH&$&+(QDIWHUWKHGDWDEDVHQDPH
7KHIROORZLQJ&211(&7VSHFLILHVEXIIHUVIRUWKHGDWDEDVHSRLQWHGWRE\WKH(03
KDQGOH
EXEC SQL
CONNECT EMP CACHE 500;

Note ,I\RXVSHFLI\DEXIIHUVL]HWKDWLVOHVVWKDQWKHVPDOOHVWRQHFXUUHQWO\LQXVHIRUWKH
GDWDEDVHWKHUHTXHVWLVLJQRUHG
7KHQH[WVWDWHPHQWRSHQVWZRGDWDEDVHV7(67DQG(03%HFDXVH&$&+(LVQRWVSHFLILHGIRU
7(67LWVEXIIHUVGHIDXOWWR(03LVRSHQHGZLWKWKH&$&+(FODXVHVSHFLI\LQJEXIIHUV
EXEC SQL
CONNECT TEST, EMP CACHE 400;

PROGRAMMER’S GUIDE 31
CHAPTER 3 WORKING WITH DATABASES

4 6SHFLI\LQJEXIIHUVIRUDOOGDWDEDVHV
7RVSHFLI\WKHVDPHQXPEHURIEXIIHUVIRUDOOGDWDEDVHVXVH&211(&7$//ZLWKWKH&$&+(
QSDUDPHWHU)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVFRQQHFWWRWZRGDWDEDVHV(03DQG
(03DQGDOORWEXIIHUVWRHDFKRIWKHP
. . .
EXEC SQL
SET DATABASE EMP = "employee.gdb";
EXEC SQL
SET DATABASE EMP2 = "test.gdb";
EXEC SQL
CONNECT ALL CACHE 400;
. . .

7KHVDPHHIIHFWFDQEHDFKLHYHGE\VSHFLI\LQJWKHVDPHDPRXQWRIFDFKHIRULQGLYLGXDO
GDWDEDVHV
. . .
EXEC SQL
CONNECT EMP CACHE 400, TEST CACHE 400;
. . .

Accessing an open database


2QFHDGDWDEDVHLVFRQQHFWHGLWVWDEOHVFDQEHDFFHVVHGDVIROORZV
g 2QHGDWDEDVHFDQEHDFFHVVHGLQDVLQJOHWUDQVDFWLRQ
g 2QHGDWDEDVHFDQEHDFFHVVHGLQPXOWLSOHWUDQVDFWLRQV
g 0XOWLSOHGDWDEDVHVFDQEHDFFHVVHGLQDVLQJOHWUDQVDFWLRQ
g 0XOWLSOHGDWDEDVHVFDQEHDFFHVVHGLQPXOWLSOHWUDQVDFWLRQV
)RUJHQHUDOLQIRUPDWLRQDERXWXVLQJWUDQVDFWLRQVVHH&KDSWHU´:RUNLQJZLWK
7UDQVDFWLRQVµ

Differentiating table names


,Q64/XVLQJPXOWLSOHGDWDEDVHVLQWUDQVDFWLRQVVRPHWLPHVUHTXLUHVH[WUDSUHFDXWLRQVWR
HQVXUHLQWHQGHGEHKDYLRU:KHQWZRRUPRUHGDWDEDVHVKDYHWDEOHVWKDWVKDUHWKHVDPHQDPH
DGDWDEDVHKDQGOHPXVWEHSUHIL[HGWRWKRVHWDEOHQDPHVWRGLIIHUHQWLDWHWKHPIURPRQH
DQRWKHULQWUDQVDFWLRQV

32 INTERBASE 5
CLOSING A DATABASE

$WDEOHQDPHGLIIHUHQWLDWHGE\DGDWDEDVHKDQGOHWDNHVWKHIRUP
handle.table

)RUH[DPSOHWKHIROORZLQJFXUVRUGHFODUDWLRQDFFHVVHVDQ(03/2<((WDEOHLQ7(67DQG
DQRWKHU(03/2<((WDEOHLQ(037(67DQG(03DUHXVHGDVSUHIL[HVWRLQGLFDWHZKLFK
(03/2<((WDEOHVKRXOGEHUHIHUHQFHG
. . .
EXEC SQL
DECLARE IDMATCH CURSOR FOR
SELECT TESTNO INTO :matchid FROM TEST.EMPLOYEE
WHERE (SELECT EMPNO FROM EMP.EMPLOYEE WHERE EMPNO = TESTNO);
. . .
Note '64/GRHVQRWVXSSRUWDFFHVVWRPXOWLSOHGDWDEDVHVLQDVLQJOHVWDWHPHQW

Closing a database
:KHQDSURJUDPLVILQLVKHGZLWKDGDWDEDVHWKHGDWDEDVHVKRXOGEHFORVHG,Q64/D
GDWDEDVHFDQEHFORVHGLQHLWKHURIWKHIROORZLQJZD\V
g ,VVXHD',6&211(&7WRGHWDFKDGDWDEDVHDQGFORVHILOHV
g $SSHQGD5(/($6(RSWLRQWRD&200,7RU52//%$&.WRGLVFRQQHFWIURPDGDWDEDVHDQG
FORVHILOHV
',6&211(&7&200,75(/($6(DQG52//%$&.5(/($6(SHUIRUPWKHIROORZLQJWDVNV
g &ORVHRSHQGDWDEDVHILOHV
g 'LVFRQQHFWIURPUHPRWHGDWDEDVHFRQQHFWLRQV
g 5HOHDVHWKHPHPRU\WKDWKROGVGDWDEDVHPHWDGDWDGHVFULSWLRQVDQG,QWHU%DVH
HQJLQHFRPSLOHGUHTXHVWV
Note &ORVLQJGDWDEDVHVZLWK',6&211(&7LVSUHIHUUHGIRUFRPSDWLELOLW\ZLWKWKH64/
VWDQGDUG'RQRWFORVHDGDWDEDVHXQWLOLWLVQRORQJHUQHHGHG2QFHFORVHGDGDWDEDVHPXVW
EHUHRSHQHGDQGLWVUHVRXUFHVUHDOORFDWHGEHIRUHLWFDQEHXVHGDJDLQ

With DISCONNECT
7RFORVHDOORSHQGDWDEDVHVE\GLVFRQQHFWLQJIURPWKHPXVHWKHIROORZLQJ',6&211(&7
V\QWD[
EXEC SQL
DISCONNECT {ALL | DEFAULT};

PROGRAMMER’S GUIDE 33
CHAPTER 3 WORKING WITH DATABASES

)RUH[DPSOHHDFKRIWKHIROORZLQJVWDWHPHQWVFORVHVDOORSHQGDWDEDVHVLQD
SURJUDP
EXEC SQL
DISCONNECT ALL;
EXEC SQL
DISCONNECT DEFAULT;

7RFORVHVSHFLILFGDWDEDVHVVSHFLI\WKHLUKDQGOHVDVFRPPDGHOLPLWHGSDUDPHWHUVXVLQJWKH
IROORZLQJV\QWD[
EXEC SQL
DISCONNECT handle [, handle ...];

)RUH[DPSOHWKHIROORZLQJVWDWHPHQWGLVFRQQHFWVIURPWZRGDWDEDVHV
EXEC SQL
DISCONNECT DB1, DB2;
Note $GDWDEDVHVKRXOGQRWEHFORVHGXQWLODOOWUDQVDFWLRQVDUHILQLVKHGZLWKLWRULWPXVWEH
UHRSHQHGDQGLWVUHVRXUFHVUHDOORFDWHG

With COMMIT and ROLLBACK


7RFORVHDOORSHQGDWDEDVHVZKHQ\RX&200,7RU52//%$&.XVHWKHIROORZLQJV\QWD[
EXEC SQL
{COMMIT | ROLLBACK} RELEASE;

)RUH[DPSOHWKHIROORZLQJ&200,7FORVHVDOORSHQGDWDEDVHV
EXEC SQL
COMMIT RELEASE;

7RFORVHVSHFLILFGDWDEDVHVSURYLGHWKHLUKDQGOHVDVSDUDPHWHUVIROORZLQJWKH5(/($6(
RSWLRQZLWK&200,7RU52//%$&.XVLQJWKHIROORZLQJV\QWD[
EXEC SQL
COMMIT | ROLLBACK RELEASE handle [, handle ...];

,QWKHIROORZLQJH[DPSOHWKH52//%$&.VWDWHPHQWFORVHVWZRGDWDEDVHV
EXEC SQL
ROLLBACK RELEASE DB1, DB2;

34 INTERBASE 5
CHAPTER

Working with Transactions


Chapter4
4
$OO64/GDWDGHILQLWLRQDQGGDWDPDQLSXODWLRQVWDWHPHQWVWDNHSODFHZLWKLQWKHFRQWH[WRID
WUDQVDFWLRQDVHWRI64/VWDWHPHQWVWKDWZRUNVWRFDUU\RXWDVLQJOHWDVN7KLVFKDSWHUH[SODLQV
KRZWRRSHQFRQWURODQGFORVHWUDQVDFWLRQVXVLQJWKHIROORZLQJ64/WUDQVDFWLRQ
PDQDJHPHQWVWDWHPHQWV

35
CHAPTER 4 WORKING WITH TRANSACTIONS

Statement Purpose
SET TRANSACTION Starts a transaction, assigns it a name, and specifies its behavior. The following
behaviors can be specified:
Access mode describes the actions a transaction’s statements can perform.
Lock resolution describes how a transaction should react if a lock conflict occurs.
Isolation level describes the view of the database given a transaction as it relates
to actions performed by other simultaneously occurring transactions.
Table reservation, an optional list of tables to lock for access at the start of the
transaction rather than at the time of explicit reads or writes.
Database specification, an optional list limiting the open databases to which a
transaction may have access.
COMMIT Saves a transaction’s changes to the database and ends the transaction.
ROLLBACK Undoes a transaction’s changes before they have been committed to the
database, and ends the transaction.
TABLE 4.1 SQL transaction management statements

7UDQVDFWLRQPDQDJHPHQWVWDWHPHQWVGHILQHWKHEHJLQQLQJDQGHQGRIDWUDQVDFWLRQ7KH\DOVR
FRQWUROLWVEHKDYLRUDQGLQWHUDFWLRQZLWKRWKHUVLPXOWDQHRXVO\UXQQLQJWUDQVDFWLRQVWKDWVKDUH
DFFHVVWRWKHVDPHGDWDZLWKLQDQGDFURVVDSSOLFDWLRQV
7KHUHDUHWZRW\SHVRIWUDQVDFWLRQVLQ,QWHU%DVH
g JGVBBWUDQVLVDGHIDXOWWUDQVDFWLRQWKDW,QWHU%DVHXVHVZKHQLWHQFRXQWHUVDVWDWHPHQW
UHTXLULQJDWUDQVDFWLRQZLWKRXWILUVWILQGLQJD6(775$16$&7,21VWDWHPHQW$GHIDXOW
EHKDYLRULVGHILQHGIRUJGVBBWUDQVEXWLWFDQEHFKDQJHGE\VWDUWLQJWKHGHIDXOWWUDQVDFWLRQ
ZLWK6(775$16$&7,21DQGVSHFLI\LQJDOWHUQDWLYHEHKDYLRUDVSDUDPHWHUV7UHDWJGVBBWUDQV
DVDJOREDOYDULDEOHRIW\SHLVFBWUBKDQGOH
Note :KHQXVLQJWKHGHIDXOWWUDQVDFWLRQZLWKRXWH[SOLFLWO\VWDUWLQJLWZLWK6(7
75$16$&7,21DSSOLFDWLRQVPXVWEHSUHSURFHVVHGZLWKRXWWKH gprePVZLWFK
g 1DPHGWUDQVDFWLRQVDUHDOZD\VVWDUWHGZLWK6(775$16$&7,21VWDWHPHQWV7KHVHVWDWHPHQWV
SURYLGHXQLTXHQDPHVIRUHDFKWUDQVDFWLRQDQGXVXDOO\LQFOXGHSDUDPHWHUVWKDWVSHFLI\D
WUDQVDFWLRQ·VEHKDYLRU
([FHSWIRUQDPLQJFRQYHQWLRQVDQGXVHLQPXOWLWUDQVDFWLRQSURJUDPVERWKWKHGHIDXOWDQG
QDPHGWUDQVDFWLRQVRIIHUWKHVDPHFRQWURORYHUWUDQVDFWLRQV6(775$16$&7,21KDV
RSWLRQDOSDUDPHWHUVIRUVSHFLI\LQJDFFHVVPRGHORFNUHVROXWLRQDQGLVRODWLRQOHYHO

36 INTERBASE 5
STARTING THE DEFAULT TRANSACTION

)RUPRUHLQIRUPDWLRQDERXWgpreVHH&KDSWHU´3UHSURFHVVLQJ&RPSLOLQJDQG /LQNLQJµ
)RUPRUHLQIRUPDWLRQDERXWWUDQVDFWLRQEHKDYLRUVHH´6SHFLI\LQJ6(775$16$&7,21
EHKDYLRUµRQSDJH 

Starting the default transaction


,IDWUDQVDFWLRQLVVWDUWHGZLWKRXWDVSHFLILHGEHKDYLRUWKHIROORZLQJGHIDXOWEHKDYLRULVXVHG
READ WRITE WAIT ISOLATION LEVEL SNAPSHOT

7KHGHIDXOWWUDQVDFWLRQLVHVSHFLDOO\XVHIXOIRUSURJUDPVWKDWXVHRQO\DVLQJOHWUDQVDFWLRQ,W
LVDXWRPDWLFDOO\VWDUWHGLQSURJUDPVWKDWUHTXLUHDWUDQVDFWLRQFRQWH[WZKHUHQRQHLVH[SOLFLWO\
SURYLGHG,WFDQDOVREHH[SOLFLWO\VWDUWHGLQDSURJUDPZLWK6(775$16$&7,21
7ROHDUQPRUHDERXWWUDQVDFWLRQEHKDYLRUVHH´6WDUWLQJWKHGHIDXOWWUDQVDFWLRQµRQSDJH 

Starting without SET TRANSACTION


6LPSOHVLQJOHWUDQVDFWLRQSURJUDPVFDQRPLW6(775$16$&7,217KHIROORZLQJSURJUDP
IUDJPHQWLVVXHVD6(/(&7VWDWHPHQWZLWKRXWVWDUWLQJDWUDQVDFWLRQ
. . .
EXEC SQL
SELECT * FROM CITIES
WHERE POPULATION > 4000000
ORDER BY POPULATION, CITY;
. . .

$SURJUDPPHUQHHGRQO\VWDUWWKHGHIDXOWWUDQVDFWLRQH[SOLFLWO\LQDVLQJOHWUDQVDFWLRQ
SURJUDPWRPRGLI\LWVRSHUDWLQJFKDUDFWHULVWLFVRUZKHQZULWLQJD'64/DSSOLFDWLRQWKDWLV
SUHSURFHVVHGZLWKWKHgpre -mVZLWFK
'XULQJSUHSURFHVVLQJZKHQgpreHQFRXQWHUVDVWDWHPHQWVXFKDV6(/(&7WKDWUHTXLUHVD
WUDQVDFWLRQFRQWH[WZLWKRXWILUVWILQGLQJD6(775$16$&7,21VWDWHPHQWLWDXWRPDWLFDOO\
JHQHUDWHVDGHIDXOWWUDQVDFWLRQDVORQJDVWKH-mVZLWFKLVQRWVSHFLILHG$GHIDXOWWUDQVDFWLRQ
VWDUWHGE\gpreXVHVDSUHGHILQHGRUGHIDXOWEHKDYLRUWKDWGLFWDWHVKRZWKHWUDQVDFWLRQ
LQWHUDFWVZLWKRWKHUVLPXOWDQHRXVWUDQVDFWLRQVDWWHPSWLQJWRDFFHVVWKHVDPHGDWD

,03257$17 '64/SURJUDPVVKRXOGEHSUHSURFHVVHGZLWKWKHgpre -mVZLWFKLIWKH\VWDUWDWUDQVDFWLRQ


WKURXJK'64/,QWKLVPRGHgpreGRHVQRWJHQHUDWHWKHGHIDXOWWUDQVDFWLRQDVQHHGHGEXW
LQVWHDGUHSRUWVDQHUURULIWKHUHLVQRWUDQVDFWLRQ

PROGRAMMER’S GUIDE 37
CHAPTER 4 WORKING WITH TRANSACTIONS

)RUPRUHLQIRUPDWLRQDERXWWUDQVDFWLRQEHKDYLRUVWKDWFDQEHPRGLILHGVHH´6SHFLI\LQJ
6(775$16$&7,21EHKDYLRUµRQSDJH )RUPRUHLQIRUPDWLRQDERXWXVLQJWKHgpre
-mVZLWFKVHH&KDSWHU´3UHSURFHVVLQJ&RPSLOLQJDQG /LQNLQJµ

Starting with SET TRANSACTION


6(775$16$&7,21LVVXHGZLWKRXWSDUDPHWHUVVWDUWVWKHGHIDXOWWUDQVDFWLRQJGVBBWUDQVZLWK
WKHIROORZLQJGHIDXOWEHKDYLRU
READ WRITE WAIT ISOLATION LEVEL SNAPSHOT

7KHIROORZLQJWDEOHVXPPDUL]HVWKHVHVHWWLQJV

Parameter Setting Purpose


Access mode READ WRITE Access mode. This transaction can select, insert, update, and delete
data.
Lock resolution WAIT Lock resolution. This transaction waits for locked tables and rows to
be released to see if it can then update them before reporting a lock
conflict.
Isolation level ISOLATION LEVEL SNAPSHOT This transaction receives a stable, unchanging view of the database
as it is at the moment the transaction starts; it never sees changes
made to the database by other active transactions.
TABLE 4.2 Default transaction default behavior

Note ([SOLFLWO\VWDUWLQJWKHGHIDXOWWUDQVDFWLRQLVJRRGSURJUDPPLQJSUDFWLFH,WPDNHVD
SURJUDP·VVRXUFHFRGHHDVLHUWRXQGHUVWDQG
7KHIROORZLQJVWDWHPHQWVDUHHTXLYDOHQW7KH\ERWKVWDUWWKHGHIDXOWWUDQVDFWLRQZLWKWKH
GHIDXOWEHKDYLRU
EXEC SQL
SET TRANSACTION;
EXEC SQL
SET TRANSACTION NAME gds__trans READ WRITE WAIT ISOLATION LEVEL
SNAPSHOT;

7RVWDUWWKHGHIDXOWWUDQVDFWLRQEXWFKDQJHLWVFKDUDFWHULVWLFV6(775$16$&7,21PXVWEH
XVHGWRVSHFLI\WKRVHFKDUDFWHULVWLFVWKDWGLIIHUIURPWKHGHIDXOW&KDUDFWHULVWLFVWKDWGRQRW
GLIIHUIURPWKHGHIDXOWFDQEHRPLWWHG)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVWDUWVWKHGHIDXOW
WUDQVDFWLRQIRU5($'21/<DFFHVV:$,7ORFNUHVROXWLRQDQG,62/$7,21/(9(/
61$36+27

38 INTERBASE 5
STARTING A NAMED TRANSACTION

EXEC SQL
SET TRANSACTION READ ONLY;

$VWKLVH[DPSOHLOOXVWUDWHVWKH1$0(FODXVHFDQEHRPLWWHGZKHQVWDUWLQJWKHGHIDXOW
WUDQVDFWLRQ

,03257$17 ,Q'64/FKDQJLQJWKHFKDUDFWHULVWLFVRIWKHGHIDXOWWUDQVDFWLRQLVDFFRPSOLVKHGDVZLWK
35(3$5(DQG(;(&87(LQDPDQQHUVLPLODUWRWKHRQHGHVFULEHGEXWWKHSURJUDPPXVWEH
SUHSURFHVVHGXVLQJWKHgpre -mVZLWFK
)RUPRUHLQIRUPDWLRQDERXWSUHSURFHVVLQJSURJUDPVZLWKWKH -mVZLWFKVHH&KDSWHU
´3UHSURFHVVLQJ&RPSLOLQJDQG /LQNLQJµ)RUPRUHLQIRUPDWLRQDERXWWUDQVDFWLRQEHKDYLRU
DQGPRGLILFDWLRQVHH´6SHFLI\LQJ6(775$16$&7,21EHKDYLRUµRQSDJH 

Starting a named transaction


$VLQJOHDSSOLFDWLRQFDQVWDUWVLPXOWDQHRXVWUDQVDFWLRQV,QWHU%DVHH[WHQGVWUDQVDFWLRQ
PDQDJHPHQWDQGGDWDPDQLSXODWLRQVWDWHPHQWVWRVXSSRUWWUDQVDFWLRQQDPHVXQLTXHLGHQWLILHUV
WKDWVSHFLI\ZKLFKWUDQVDFWLRQFRQWUROVDJLYHQVWDWHPHQWDPRQJWKRVHWUDQVDFWLRQVWKDWDUH
DFWLYH
7UDQVDFWLRQQDPHVPXVWEHXVHGWRGLVWLQJXLVKRQHWUDQVDFWLRQIURPDQRWKHULQSURJUDPV
WKDWXVHWZRRUPRUHWUDQVDFWLRQVDWDWLPH(DFKWUDQVDFWLRQVWDUWHGZKLOHRWKHUWUDQVDFWLRQV
DUHDFWLYHUHTXLUHVDXQLTXHQDPHDQGLWVRZQ6(775$16$&7,21VWDWHPHQW6(7
75$16$&7,21FDQLQFOXGHRSWLRQDOSDUDPHWHUVWKDWPRGLI\DWUDQVDFWLRQ·VEHKDYLRU
7KHUHDUHIRXUVWHSVIRUXVLQJWUDQVDFWLRQQDPHVLQDSURJUDP
 'HFODUHDXQLTXHKRVWODQJXDJHYDULDEOHIRUHDFKWUDQVDFWLRQQDPH,Q&DQG
&WUDQVDFWLRQQDPHVVKRXOGEHGHFODUHGDVORQJSRLQWHUV
 ,QLWLDOL]HHDFKWUDQVDFWLRQQDPHWR]HUR
 8VH6(775$16$&7,21WRVWDUWHDFKWUDQVDFWLRQXVLQJDQDYDLODEOHWUDQVDFWLRQ
QDPH
 ,QFOXGHWKHWUDQVDFWLRQQDPHLQVXEVHTXHQWWUDQVDFWLRQPDQDJHPHQWDQGGDWD
PDQLSXODWLRQVWDWHPHQWVWKDWVKRXOGEHFRQWUROOHGE\DVSHFLILHGWUDQVDFWLRQ

,03257$17 8VLQJQDPHGWUDQVDFWLRQVLQG\QDPLF64/VWDWHPHQWVLVVRPHZKDWGLIIHUHQW)RU
LQIRUPDWLRQDERXWQDPHGWUDQVDFWLRQVLQ'64/VHH´:RUNLQJZLWKPXOWLSOHWUDQVDFWLRQVLQ
'64/µRQSDJH 
)RUDGGLWLRQDOLQIRUPDWLRQDERXWFUHDWLQJPXOWLSOHWUDQVDFWLRQSURJUDPVVHH´:RUNLQJZLWK
PXOWLSOHWUDQVDFWLRQVµRQSDJH 

PROGRAMMER’S GUIDE 39
CHAPTER 4 WORKING WITH TRANSACTIONS

Naming transactions
$WUDQVDFWLRQQDPHLVDSURJUDPPHUVXSSOLHGYDULDEOHWKDWGLVWLQJXLVKHVRQHWUDQVDFWLRQ
IURPDQRWKHULQ64/VWDWHPHQWV,IWUDQVDFWLRQQDPHVDUHQRWXVHGLQ64/VWDWHPHQWVWKDW
FRQWUROWUDQVDFWLRQVDQGPDQLSXODWHGDWDWKHQWKRVHVWDWHPHQWVRSHUDWHRQO\RQWKHGHIDXOW
WUDQVDFWLRQJGVBBWUDQV
7KHIROORZLQJ&FRGHGHFODUHVDQGLQLWLDOL]HVWZRWUDQVDFWLRQQDPHVXVLQJWKHLVFBWUBKDQGOH
GDWDW\SH,WWKHQVWDUWVWKRVHWUDQVDFWLRQVLQ6(775$16$&7,21 VWDWHPHQWV
. . .
EXEC SQL
BEGIN DECLARE SECTION;
isc_tr_handle t1, t2; /* declare transaction names */
EXEC SQL
END DECLARE SECTION;
. . .
t1 = t2 = (isc_tr_handle) NULL; /* initialize names to zero */
. . .
EXEC SQL
SET TRANSACTION NAME t1; /* start trans. w. default behavior */
EXEC SQL
SET TRANSACTION NAME t2; /* start trans2. w. default behavior */
. . .

(DFKRIWKHVHVWHSVLVIXOO\GHVFULEHGLQWKHIROORZLQJVHFWLRQV
$WUDQVDFWLRQQDPHFDQEHLQFOXGHGDVDQRSWLRQDOSDUDPHWHULQDQ\GDWDPDQLSXODWLRQDQG
WUDQVDFWLRQPDQDJHPHQWVWDWHPHQW,QPXOWLWUDQVDFWLRQSURJUDPVRPLWWLQJDWUDQVDFWLRQ
QDPHFDXVHVDVWDWHPHQWWREHH[HFXWHGIRUWKHGHIDXOWWUDQVDFWLRQJGVBBWUDQV
)RUPRUHLQIRUPDWLRQDERXWXVLQJWUDQVDFWLRQQDPHVZLWKGDWDPDQLSXODWLRQVWDWHPHQWVVHH
&KDSWHU´:RUNLQJZLWK'DWDµ

4 'HFODULQJWUDQVDFWLRQQDPHV
7UDQVDFWLRQQDPHVPXVWEHGHFODUHGEHIRUHWKH\FDQEHXVHG$QDPHLVGHFODUHGDVD
KRVWODQJXDJHSRLQWHU,Q&DQG&WUDQVDFWLRQQDPHVVKRXOGEHGHFODUHGDVORQJSRLQWHUV
7KHIROORZLQJFRGHLOOXVWUDWHVKRZWRGHFODUHWZRWUDQVDFWLRQQDPHV
EXEC SQL
BEGIN DECLARE SECTION;
isc_tr_handle t1;
isc_tr_handle t2;
EXEC SQL
END DECLARE SECTION;

40 INTERBASE 5
STARTING A NAMED TRANSACTION

Note ,QWKLVH[DPSOHWKHWUDQVDFWLRQGHFODUDWLRQRFFXUVZLWKLQDQ64/VHFWLRQGHFODUDWLRQ
:KLOH,QWHU%DVHGRHVQRWUHTXLUHWKDWKRVWODQJXDJHYDULDEOHVRFFXUZLWKLQDVHFWLRQ
GHFODUDWLRQSXWWLQJWKHPWKHUHJXDUDQWHHVFRPSDWLELOLW\ZLWKRWKHU64/LPSOHPHQWDWLRQV
WKDWGRUHTXLUHVHFWLRQGHFODUDWLRQV
7UDQVDFWLRQQDPHVDUHXVXDOO\GHFODUHGJOREDOO\DWWKHPRGXOHOHYHO,IDWUDQVDFWLRQQDPHLV
GHFODUHGORFDOO\HQVXUHWKDW
g 7KHWUDQVDFWLRQXVLQJWKHQDPHLVFRPSOHWHO\FRQWDLQHGZLWKLQWKHIXQFWLRQZKHUHWKHQDPH
LVGHFODUHG,QFOXGHDQHUURUKDQGOLQJURXWLQHWRUROOEDFNWUDQVDFWLRQVZKHQHUURUVRFFXU
52//%$&.UHOHDVHVDWUDQVDFWLRQQDPHDQGVHWVLWVYDOXHWR18//
g 7KHWUDQVDFWLRQQDPHLVQRWXVHGRXWVLGHWKHIXQFWLRQZKHUHLWLVGHFODUHG
7RUHIHUHQFHDWUDQVDFWLRQQDPHGHFODUHGLQDQRWKHUPRGXOHSURYLGHDQH[WHUQDOGHFODUDWLRQ
IRULW)RUH[DPSOHLQ&WKHH[WHUQDOGHFODUDWLRQIRUWDQGWPLJKWEHDVIROORZV
EXEC SQL
BEGIN DECLARE SECTION;
extern isc_tr_handle t1, t2;
EXEC SQL
END DECLARE SECTION;

4 ,QLWLDOL]LQJWUDQVDFWLRQQDPHV
2QFHWUDQVDFWLRQQDPHVDUHGHFODUHGWKH\VKRXOGEHLQLWLDOL]HGWR]HUREHIRUHEHLQJXVHGIRU
WKHILUVWWLPH7KHIROORZLQJ&FRGHLOOXVWUDWHVKRZWRVHWDVWDUWLQJYDOXHIRUWZRGHFODUHG
WUDQVDFWLRQQDPHV
t1 = t2 = (isc_tr_handle) NULL; /* initialize transaction names to zero */

2QFHDWUDQVDFWLRQQDPHLVGHFODUHGDQGLQLWLDOL]HGLWFDQEHXVHGWR
g 6WDUWDQGQDPHDWUDQVDFWLRQ8VLQJDWUDQVDFWLRQQDPHIRUDOOWUDQVDFWLRQVH[FHSWIRUWKH
GHIDXOWWUDQVDFWLRQLVUHTXLUHGLIDSURJUDPUXQVPXOWLSOHVLPXOWDQHRXVWUDQVDFWLRQV
g 6SHFLI\ZKLFKWUDQVDFWLRQVFRQWUROGDWDPDQLSXODWLRQVWDWHPHQWV7UDQVDFWLRQQDPHVDUH
UHTXLUHGLQPXOWLWUDQVDFWLRQSURJUDPVXQOHVVDVWDWHPHQWDIIHFWVRQO\WKHGHIDXOW
WUDQVDFWLRQ
g &RPPLWRUUROOEDFNVSHFLILFWUDQVDFWLRQVLQDPXOWLWUDQVDFWLRQSURJUDP

Specifying SET TRANSACTION behavior


8VH6(775$16$&7,21WRVWDUWDQDPHGWUDQVDFWLRQDQGRSWLRQDOO\VSHFLI\LWVEHKDYLRU7KH
V\QWD[IRUVWDUWLQJDQDPHGWUDQVDFWLRQXVLQJGHIDXOWEHKDYLRULV
SET TRANSACTION NAME name;

PROGRAMMER’S GUIDE 41
CHAPTER 4 WORKING WITH TRANSACTIONS

)RUDVXPPDU\RIWKHGHIDXOWEHKDYLRUIRUDWUDQVDFWLRQVWDUWHGZLWKRXWVSHFLI\LQJEHKDYLRU
SDUDPHWHUVVHHWDEOHRQSDJH7KHIROORZLQJVWDWHPHQWVDUHHTXLYDOHQWWKH\ERWKVWDUW
WKHWUDQVDFWLRQQDPHGWXVLQJGHIDXOWWUDQVDFWLRQEHKDYLRU
EXEC SQL
SET TRANSACTION NAME t1;
EXEC SQL
SET TRANSACTION NAME t1 READ WRITE WAIT ISOLATION LEVEL SNAPSHOT;
7KHIROORZLQJWDEOHOLVWVWKHRSWLRQDO6(775$16$&7,21SDUDPHWHUVIRUVSHFLI\LQJWKH
EHKDYLRURIWKHGHIDXOWWUDQVDFWLRQ

Parameter Setting Purpose


Access Mode READ ONLY or READ WRITE Describes the type of access this transaction is permitted
for a table. For more information about access mode, see
“Access mode” on page 44.
Lock Resolution WAIT or NO WAIT Specifies what happens when this transaction
encounters a locked row during an update or delete. It
either waits for the lock to be released so it can attempt
to complete its actions, or it returns an immediate lock
conflict error message. For more information about lock
resolution, see “Lock resolution” on page 50.
TABLE 4.3 SET TRANSACTION parameters

42 INTERBASE 5
STARTING A NAMED TRANSACTION

Parameter Setting Purpose


Isolation Level SNAPSHOT provides a view of the database at the Determines this transaction’s interaction with other
moment this transaction starts, but prevents simultaneous transactions attempting to access the
viewing changes made by other active same tables.
transactions.
READ COMMITTED isolation level also enables a user to
SNAPSHOT TABLE STABILITY prevents other specify which version of a row it can read. There are two
transactions from making changes to tables that options:
this transaction is reading and updating, but
• RECORD_VERSION: the transaction immediately reads the
permits them to read rows in the table. latest committed version of a requested row, even if a
READ COMMITTED reads the most recently more recent uncommitted version also resides on disk.
committed version of a row during updates and • NO RECORD_VERSION: if an uncommitted version of the
deletions, and allows this transaction to make requested row is present and WAIT lock resolution is
changes if there is no update conflict with other specified, the transaction waits until the committed
transactions. version of the row is also the latest version; if NO WAIT is
specified, the transaction immediately returns an error
(“deadlock”) if the committed version is not the most
recent version.
Table RESERVING RESERVING specifies a subset of available tables to lock
Reservation immediately for this transaction to access.
Database USING USING specifies a subset of available databases that this
Specification transaction can access; it cannot access any other
databases. The purpose of this option is to reduce the
amount of system resources used by this transaction.
Note: USING is not available in DSQL.
TABLE 4.3 SET TRANSACTION parameters (continued)

7KHFRPSOHWHV\QWD[RI6(775$16$&7,21LV
EXEC SQL
SET TRANSACTION [NAME name]
[READ WRITE| READ ONLY]
[WAIT | NO WAIT]
[[ISOLATION LEVEL] {SNAPSHOT [TABLE STABILITY]
| READ COMMITTED [[NO] RECORD_VERSION]}]
[RESERVING <reserving_clause>
| USING dbhandle [, dbhandle ...]];
<reserving_clause> = table [, table ...]
[FOR [SHARED | PROTECTED] {READ | WRITE}] [, <reserving_clause>]

7UDQVDFWLRQRSWLRQVDUHIXOO\GHVFULEHGLQWKHIROORZLQJVHFWLRQV

PROGRAMMER’S GUIDE 43
CHAPTER 4 WORKING WITH TRANSACTIONS

4 $FFHVVPRGH
7KHDFFHVVPRGHSDUDPHWHUVSHFLILHVWKHW\SHRIDFFHVVDWUDQVDFWLRQKDVIRUWKHWDEOHVLWXVHV
7KHUHDUHWZRSRVVLEOHVHWWLQJV
g 5($'21/<VSHFLILHVWKDWDWUDQVDFWLRQFDQVHOHFWGDWDIURPDWDEOHEXWFDQQRWLQVHUW
XSGDWHRUGHOHWHWDEOHGDWD
g 5($':5,7(VSHFLILHVWKDWDWUDQVDFWLRQFDQVHOHFWLQVHUWXSGDWHDQGGHOHWHWDEOHGDWD7KLV
LVWKHGHIDXOWVHWWLQJLIQRQHLVVSHFLILHG
,QWHU%DVHDVVXPHVWKDWPRVWWUDQVDFWLRQVERWKUHDGDQGZULWHGDWD:KHQVWDUWLQJD
WUDQVDFWLRQIRUUHDGLQJDQGZULWLQJ5($':5,7(FDQEHRPLWWHGIURP6(775$16$&7,21
VWDWHPHQW)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVVWDUWDWUDQVDFWLRQWIRU5($':5,7(
DFFHVV
EXEC SQL
SET TRANSACTION NAME t1;
EXEC SQL
SET TRANSACTION NAME t1 READ WRITE;

7,3 ,WLVJRRGSURJUDPPLQJSUDFWLFHWRVSHFLI\DWUDQVDFWLRQ·VDFFHVVPRGHHYHQZKHQLWLV
5($':5,7(,WPDNHVDQDSSOLFDWLRQ·VVRXUFHFRGHHDVLHUWRUHDGDQGGHEXJEHFDXVHWKH
SURJUDP·VLQWHQWLRQVDUHFOHDUO\VSHOOHGRXW
6WDUWDWUDQVDFWLRQIRU5($'21/<DFFHVVZKHQ\RXRQO\QHHGWRUHDGGDWD5($'21/<
PXVWEHVSHFLILHG)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVWDUWVDWUDQVDFWLRQWIRUUHDGRQO\
DFFHVV
EXEC SQL
SET TRANSACTION NAME t1 READ ONLY;

4 ,VRODWLRQOHYHO
7KHLVRODWLRQOHYHOSDUDPHWHUVSHFLILHVWKHFRQWURODWUDQVDFWLRQH[HUFLVHVRYHUWDEOHDFFHVV,W
GHWHUPLQHVWKH
g 9LHZRIDGDWDEDVHWKHWUDQVDFWLRQFDQVHH
g 7DEOHDFFHVVDOORZHGWRWKLVDQGRWKHUVLPXOWDQHRXVWUDQVDFWLRQV

44 INTERBASE 5
STARTING A NAMED TRANSACTION

7KHIROORZLQJWDEOHGHVFULEHVWKHWKUHHLVRODWLRQOHYHOVVXSSRUWHGE\,QWHU%DVH

Isolation level Purpose


SNAPSHOT The default isolation level: provides a stable, committed view of the database at the time the
transaction starts. Other simultaneous transactions can UPDATE and INSERT rows, but this
transaction cannot see those changes. For updated rows, this transaction sees versions of
those rows as they existed at the start of the transaction. If this transaction attempts to update
or delete rows changed by another transaction, an update conflict is reported.
SNAPSHOT TABLE STABILITY Provides a transaction sole insert, update, and delete access to the tables it uses. Other
simultaneous transactions may still be able to select rows from those tables.
READ COMMITTED Enables the transaction to see all committed data in the database, and to update rows
updated and committed by other simultaneous transactions without causing lost update
problems.
TABLE 4.4 ISOLATION LEVEL options

7KHLVRODWLRQOHYHOIRUPRVWWUDQVDFWLRQVVKRXOGEHHLWKHU61$36+27RU5($'&200,77('
7KHVHOHYHOVHQDEOHVLPXOWDQHRXVWUDQVDFWLRQVWRVHOHFWLQVHUWXSGDWHDQGGHOHWHGDWDLQ
VKDUHGGDWDEDVHVDQGWKH\PLQLPL]HWKHFKDQFHIRUORFNFRQIOLFWV/RFNFRQIOLFWVRFFXULQWZR
VLWXDWLRQV
g :KHQDWUDQVDFWLRQDWWHPSWVWRXSGDWHDURZDOUHDG\XSGDWHGRUGHOHWHGE\DQRWKHU
WUDQVDFWLRQ$URZXSGDWHGE\DWUDQVDFWLRQLVHIIHFWLYHO\ORFNHGIRUXSGDWHWRDOORWKHU
WUDQVDFWLRQVXQWLOWKHFRQWUROOLQJWUDQVDFWLRQFRPPLWVRUUROOVEDFN5($'&200,77('
WUDQVDFWLRQVFDQUHDGDQGXSGDWHURZVXSGDWHGE\VLPXOWDQHRXVWUDQVDFWLRQVDIWHUWKH\
FRPPLW
g :KHQDWUDQVDFWLRQDWWHPSWVWRLQVHUWXSGDWHRUGHOHWHDURZLQDWDEOHORFNHGE\DQRWKHU
WUDQVDFWLRQZLWKDQLVRODWLRQOHYHORI61$36+277$%/(67$%,/,7<61$36+277$%/(
67$%,/,7<ORFNVHQWLUHWDEOHVIRUZULWHDFFHVVDOWKRXJKFRQFXUUHQWUHDGVE\RWKHU
61$36+27DQG5($'&200,77('WUDQVDFWLRQVDUHSHUPLWWHG
8VLQJ61$36+277$%/(67$%,/,7<JXDUDQWHHVWKDWRQO\DVLQJOHWUDQVDFWLRQFDQPDNH
FKDQJHVWRWDEOHVEXWLQFUHDVHVWKHFKDQFHRIORFNFRQIOLFWVZKHUHWKHUHDUHVLPXOWDQHRXV
WUDQVDFWLRQVDWWHPSWLQJWRDFFHVVWKHVDPHWDEOHV)RUPRUHLQIRUPDWLRQDERXWWKHOLNHOLKRRG
RIORFNFRQIOLFWVVHH´,VRODWLRQOHYHOLQWHUDFWLRQVµRQSDJH 

COMPARING SNAPSHOT, READ COMMITTED,


AND SNAPSHOT TABLE STABILITY
7KHUHDUHILYHFODVVLFSUREOHPVDOOWUDQVDFWLRQPDQDJHPHQWVWDWHPHQWVPXVWDGGUHVV
g /RVWXSGDWHVZKLFKFDQRFFXULIDQXSGDWHLVRYHUZULWWHQE\DVLPXOWDQHRXVWUDQVDFWLRQ
XQDZDUHRIWKHODVWXSGDWHVPDGHE\DQRWKHUWUDQVDFWLRQ

PROGRAMMER’S GUIDE 45
CHAPTER 4 WORKING WITH TRANSACTIONS

g 'LUW\UHDGVZKLFKFDQRFFXULIWKHV\VWHPDOORZVRQHWUDQVDFWLRQWRVHOHFWXQFRPPLWWHG
FKDQJHVPDGHE\DQRWKHUWUDQVDFWLRQ
g 1RQUHSURGXFLEOHUHDGVZKLFKFDQRFFXULIRQHWUDQVDFWLRQLVDOORZHGWRXSGDWHRUGHOHWHURZV
WKDWDUHUHSHDWHGO\VHOHFWHGE\DQRWKHUWUDQVDFWLRQ5($'&200,77('WUDQVDFWLRQVSHUPLW
QRQUHSURGXFLEOHUHDGVE\GHVLJQVLQFHWKH\FDQVHHFRPPLWWHGGHOHWHVPDGHE\RWKHU
WUDQVDFWLRQV
g 3KDQWRPURZVZKLFKFDQRFFXULIRQHWUDQVDFWLRQLVDOORZHGWRVHOHFWVRPHEXWQRWDOOQHZ
URZVZULWWHQE\DQRWKHUWUDQVDFWLRQ5($'&200,77('WUDQVDFWLRQVGRQRWSUHYHQW
SKDQWRPURZV
g 8SGDWHVLGHHIIHFWVZKLFKFDQRFFXUZKHQURZYDOXHVDUHLQWHUGHSHQGHQWDQGWKHLU
GHSHQGHQFLHVDUHQRWDGHTXDWHO\SURWHFWHGRUHQIRUFHGE\ORFNLQJWULJJHUVRULQWHJULW\
FRQVWUDLQWV7KHVHFRQIOLFWVRFFXUZKHQWZRRUPRUHVLPXOWDQHRXVWUDQVDFWLRQVUDQGRPO\
DQGUHSHDWHGO\DFFHVVDQGXSGDWHWKHVDPHGDWDVXFKWUDQVDFWLRQVDUHFDOOHGLQWHUOHDYHG
WUDQVDFWLRQV
([FHSWDVQRWHGDOOWKUHH,QWHU%DVHLVRODWLRQOHYHOVFRQWUROWKHVHSUREOHPV7KHIROORZLQJ
WDEOHVXPPDUL]HVKRZDWUDQVDFWLRQZLWKDSDUWLFXODULVRODWLRQOHYHOFRQWUROVDFFHVVWRLWVGDWD
IRURWKHUVLPXOWDQHRXVWUDQVDFWLRQV

Problem SNAPSHOT, READ COMMITTED SNAPSHOT TABLE STABILITY


Lost updates Other transactions cannot update rows already Other transactions cannot update tables
updated by this transaction. controlled by this transaction.
Dirty reads Other SNAPSHOT transactions can only read a Other transactions cannot access tables updated
previous version of a row updated by this by this transaction.
transaction.
Other READ COMMITTED transactions can only read
a previous version, or committed updates.
TABLE 4.5 InterBase management of classic transaction conflicts

46 INTERBASE 5
STARTING A NAMED TRANSACTION

Problem SNAPSHOT, READ COMMITTED SNAPSHOT TABLE STABILITY


Non-reproducible SNAPSHOT and SNAPSHOT TABLE STABILITY SNAPSHOT and SNAPSHOT TABLE STABILITY
reads transactions can only read versions of rows transactions can only read versions of rows
committed when they started. committed when they started.
READ COMMITTED transactions must expect that Other transactions cannot access tables updated
reads cannot be reproduced. by this transaction.
Phantom rows READ COMMITTED transactions may encounter Other transactions cannot access tables
phantom rows. controlled by this transaction.
Update side effects Other SNAPSHOT transactions can only read a Other transactions cannot update tables
previous version of a row updated by this controlled by this transaction.
transaction.
Use triggers and integrity constraints to avoid
Other READ COMMITTED transactions can only read any problems with interleaved transactions.
a previous version, or committed updates.
Use triggers and integrity constraints to try to
avoid any problems with interleaved
transactions.
TABLE 4.5 InterBase management of classic transaction conflicts (continued)

CHOOSING BETWEEN SNAPSHOT AND READ COMMITTED


7KHFKRLFHEHWZHHQ61$36+27DQG5($'&200,77('LVRODWLRQOHYHOVGHSHQGVRQDQ
DSSOLFDWLRQ·VQHHGV61$36+27LVWKHGHIDXOW,QWHU%DVHLVRODWLRQOHYHO5($'&200,77('
GXSOLFDWHV61$36+27EHKDYLRUEXWFDQUHDGVXEVHTXHQWFKDQJHVFRPPLWWHGE\RWKHU
WUDQVDFWLRQV,QPDQ\FDVHVXVLQJ5($'&200,77('UHGXFHVGDWDFRQWHQWLRQ
61$36+27WUDQVDFWLRQVUHFHLYHDVWDEOHYLHZRIDGDWDEDVHDVLWH[LVWVWKHPRPHQWWKH
WUDQVDFWLRQVVWDUW5($'&200,77('WUDQVDFWLRQVFDQVHHWKHODWHVWFRPPLWWHGYHUVLRQVRI
URZV%RWKW\SHVRIWUDQVDFWLRQVFDQXVH6(/(&7VWDWHPHQWVXQOHVVWKH\HQFRXQWHUWKH
IROORZLQJFRQGLWLRQV
g 7DEOHORFNHGE\61$36+277$%/(67$%,/,7<WUDQVDFWLRQIRU83'$7(
g 8QFRPPLWWHGLQVHUWVPDGHE\RWKHUVLPXOWDQHRXVWUDQVDFWLRQV,QWKLVFDVHD6(/(&7LV
DOORZHGEXWFKDQJHVFDQQRWEHVHHQ
5($'&200,77('WUDQVDFWLRQVFDQUHDGWKHODWHVWFRPPLWWHGYHUVLRQRIURZV$
61$36+27WUDQVDFWLRQFDQUHDGRQO\DSULRUYHUVLRQRIWKHURZDVLWH[LVWHGEHIRUHWKHXSGDWH
RFFXUUHG
61$3+27DQG5($'&200,77('WUDQVDFWLRQVZLWK5($':5,7(DFFHVVFDQXVH,16(57
83'$7(DQG'(/(7(XQOHVVWKH\HQFRXQWHUWDEOHVORFNHGE\61$36+277$%/(67$%,/,7<
WUDQVDFWLRQV

PROGRAMMER’S GUIDE 47
CHAPTER 4 WORKING WITH TRANSACTIONS

61$36+27WUDQVDFWLRQVFDQQRWXSGDWHRUGHOHWHURZVSUHYLRXVO\XSGDWHGRUGHOHWHGDQGWKHQ
FRPPLWWHGE\RWKHUVLPXOWDQHRXVWUDQVDFWLRQV$WWHPSWLQJWRXSGDWHDURZSUHYLRXVO\
XSGDWHGRUGHOHWHGE\DQRWKHUWUDQVDFWLRQUHVXOWVLQDQXSGDWHFRQIOLFWHUURU
$5($'&200,77('5($':5,7(WUDQVDFWLRQFDQUHDGFKDQJHVFRPPLWWHGE\RWKHU
WUDQVDFWLRQVDQGVXEVHTXHQWO\XSGDWHWKRVHFKDQJHGURZV
2FFDVLRQDOXSGDWHFRQIOLFWVPD\RFFXUZKHQVLPXOWDQHRXV61$36+27DQG5($'
&200,77('WUDQVDFWLRQVDWWHPSWWRXSGDWHWKHVDPHURZDWWKHVDPHWLPH:KHQXSGDWH
FRQIOLFWVRFFXUH[SHFWWKHIROORZLQJEHKDYLRU
g )RUPDVVRUVHDUFKHGXSGDWHVXSGDWHVZKHUHDVLQJOH83'$7(PRGLILHVPXOWLSOHURZVLQDWDEOH
DOOXSGDWHVDUHXQGRQHRQFRQIOLFW7KH83'$7(FDQEHUHWULHG)RU5($'&200,77('
WUDQVDFWLRQVWKH125(&25'B9(56,21RSWLRQFDQEHXVHGWRQDUURZWKHZLQGRZEHWZHHQ
UHDGVDQGXSGDWHVRUGHOHWHV)RUPRUHLQIRUPDWLRQVHH´6WDUWLQJDWUDQVDFWLRQZLWK5($'
&200,77('LVRODWLRQOHYHOµRQSDJH 
g )RUFXUVRURUSRVLWLRQHGXSGDWHVZKHUHURZVDUHUHWULHYHGDQGXSGDWHGIURPDQDFWLYHVHWRQH
URZDWDWLPHRQO\DVLQJOHXSGDWHLVXQGRQH7RUHWU\WKHXSGDWHWKHFXUVRUPXVWEHFORVHG
WKHQUHRSHQHGDQGXSGDWHVUHVXPHGDWWKHSRLQWRISUHYLRXVFRQIOLFW
)RUPRUHLQIRUPDWLRQDERXW83'$7(WKURXJKFXUVRUVVHH&KDSWHU´:RUNLQJZLWK'DWDµ

STARTING A TRANSACTION WITH SNAPSHOT ISOLATION LEVEL


,QWHU%DVHDVVXPHVWKDWWKHGHIDXOWLVRODWLRQOHYHOIRUWUDQVDFWLRQVLV61$36+277KHUHIRUH
61$36+27QHHGQRWEHVSHFLILHGLQ6(775$16$&7,21WRVHWWKHLVRODWLRQOHYHO)RU
H[DPSOHWKHIROORZLQJVWDWHPHQWVDUHHTXLYDOHQW7KH\ERWKVWDUWDWUDQVDFWLRQWIRU5($'
:5,7(DFFHVVDQGVHWLVRODWLRQOHYHOWR61$36+27
EXEC SQL
SET TRANSACTION NAME t1;
EXEC SQL
SET TRANSACTION NAME t1 READ WRITE SNAPSHOT;

:KHQDQLVRODWLRQOHYHOLVVSHFLILHGLWPXVWIROORZWKHDFFHVVDQGORFNUHVROXWLRQPRGHV

7,3 ,WLVJRRGSURJUDPPLQJSUDFWLFHWRVSHFLI\DWUDQVDFWLRQ·VLVRODWLRQOHYHOHYHQZKHQLWLV
61$36+27,WPDNHVDQDSSOLFDWLRQ·VVRXUFHFRGHHDVLHUWRUHDGDQGGHEXJEHFDXVHWKH
SURJUDP·VLQWHQWLRQVDUHFOHDUO\VSHOOHGRXW

STARTING A TRANSACTION WITH READ COMMITTED ISOLATION LEVEL


7RVWDUWD5($'&200,77('WUDQVDFWLRQWKHLVRODWLRQOHYHOPXVWEHVSHFLILHG)RUH[DPSOH
WKHIROORZLQJVWDWHPHQWVWDUWVDQDPHGWUDQVDFWLRQWIRU5($':5,7(DFFHVVDQGVHWV
LVRODWLRQOHYHOWR5($'&200,77('

48 INTERBASE 5
STARTING A NAMED TRANSACTION

EXEC SQL
SET TRANSACTION NAME t1 READ WRITE READ COMMITTED;

,VRODWLRQOHYHODOZD\VIROORZVDFFHVVPRGH,IWKHDFFHVVPRGHLVRPLWWHGLVRODWLRQOHYHOLVWKH
ILUVWSDUDPHWHUWRIROORZWKHWUDQVDFWLRQQDPH
5($'&200,77('VXSSRUWVPXWXDOO\H[FOXVLYHRSWLRQDOSDUDPHWHUV5(&25'B9(56,21
DQG125(&25'B9(56,21ZKLFKGHWHUPLQHWKH5($'&200,77('EHKDYLRUZKHQLW
HQFRXQWHUVDURZZKHUHWKHODWHVWYHUVLRQRIWKDWURZLVXQFRPPLWWHG
g 5(&25'B9(56,21VSHFLILHVWKDWWKHWUDQVDFWLRQLPPHGLDWHO\UHDGVWKHODWHVWFRPPLWWHG
YHUVLRQRIDURZHYHQLIDPRUHUHFHQWXQFRPPLWWHGYHUVLRQDOVRUHVLGHVRQGLVN
g 125(&25'B9(56,21WKHGHIDXOWVSHFLILHVWKDWWKHWUDQVDFWLRQFDQRQO\UHDGWKHODWHVW
YHUVLRQRIDUHTXHVWHGURZ,IWKH:$,7ORFNUHVROXWLRQRSWLRQLVDOVRVSHFLILHGWKHQWKH
WUDQVDFWLRQZDLWVXQWLOWKHODWHVWYHUVLRQRIDURZLVFRPPLWWHGRUUROOHGEDFNDQGUHWULHVLWV
UHDG,IWKH12:$,7RSWLRQLVVSHFLILHGWKHWUDQVDFWLRQUHWXUQVDQLPPHGLDWHGHDGORFN
HUURU
%HFDXVH125(&25'B9(56,21LVWKHGHIDXOWEHKDYLRULWQHHGQRWEHVSHFLILHGZLWK5($'
&20,77(')RUH[DPSOHWKHIROORZLQJVWDWHPHQWVDUHHTXLYDOHQW7KH\VWDUWDQDPHG
WUDQVDFWLRQWIRU5($':5,7(DFFHVVDQGVHWLVRODWLRQOHYHOWR5($'&200,77('12
5(&25'B9(56,21
EXEC SQL
SET TRANSACTION NAME t1 READ WRITE READ COMMITTED;
EXEC SQL
SET TRANSACTION NAME t1 READ WRITE READ COMMITTED
NO RECORD_VERSION;

5(&25'B9(56,21PXVWDOZD\VEHVSHFLILHGZKHQLWLVXVHG)RUH[DPSOHWKHIROORZLQJ
VWDWHPHQWVWDUWVDQDPHGWUDQVDFWLRQWIRU5($':5,7(DFFHVVDQGVHWVLVRODWLRQOHYHOWR
5($'&200,77('5(&25'B9(56,21
EXEC SQL
SET TRANSACTION NAME t1 READ WRITE READ COMMITTED
RECORD_VERSION;

STARTING A TRANSACTION WITH


SNAPSHOT TABLE STABILITY ISOLATION LEVEL
7RVWDUWD61$36+277$%/(67$%,/,7<WUDQVDFWLRQWKHLVRODWLRQOHYHOPXVWEHVSHFLILHG)RU
H[DPSOHWKHIROORZLQJVWDWHPHQWVWDUWVDQDPHGWUDQVDFWLRQWIRU5($':5,7(DFFHVVDQG
VHWVLVRODWLRQOHYHOWR61$36+277$%/(67$%,/,7<
EXEC SQL
SET TRANSACTION NAME t1 READ WRITE SNAPSHOT TABLE STABILITY;

PROGRAMMER’S GUIDE 49
CHAPTER 4 WORKING WITH TRANSACTIONS

,VRODWLRQOHYHODOZD\VIROORZVWKHRSWLRQDODFFHVVPRGHDQGORFNUHVROXWLRQSDUDPHWHUVLIWKH\
DUHSUHVHQW

,03257$17 8VH61$36+277$%/(67$%,/,7<ZLWKFDUH,QDQHQYLURQPHQWZKHUHPXOWLSOH
WUDQVDFWLRQVVKDUHGDWDEDVHDFFHVV61$36+277$%/(67$%,/,7<JUHDWO\LQFUHDVHVWKH
OLNHOLKRRGRIORFNFRQIOLFWV

ISOLATION LEVEL INTERACTIONS


7RGHWHUPLQHWKHSRVVLELOLW\IRUORFNFRQIOLFWVEHWZHHQWZRWUDQVDFWLRQVDFFHVVLQJWKHVDPH
GDWDEDVHHDFKWUDQVDFWLRQ·VLVRODWLRQOHYHODQGDFFHVVPRGHPXVWEHFRQVLGHUHG7KH
IROORZLQJWDEOHVXPPDUL]HVSRVVLEOHFRPELQDWLRQV

SNAPSHOT or READ COMMITTED SNAPSHOT TABLE STABILITY


UPDATE SELECT UPDATE SELECT
SNAPSHOT or UPDATE Some simultaneous — Always conflicts Always conflicts.
READ COMMITTED updates may conflict
SELECT — — — —
SNAPSHOT TABLE UPDATE Always conflicts — Always conflicts Always conflicts.
STABILITY
SELECT Always conflicts — Always conflicts —
TABLE 4.6 Isolation level Interaction with SELECT and UPDATE

$VWKLVWDEOHLOOXVWUDWHV61$36+27DQG5($'&200,77('WUDQVDFWLRQVRIIHUWKHOHDVW
FKDQFHIRUFRQIOLFWV)RUH[DPSOHLIWLVD61$36+27WUDQVDFWLRQZLWK5($':5,7(
DFFHVVDQGWLVD5($'&200,77('WUDQVDFWLRQZLWK5($':5,7(DFFHVVWDQGWRQO\
FRQIOLFWZKHQWKH\DWWHPSWWRXSGDWHWKHVDPHURZV,IWDQGWKDYH5($'21/<DFFHVV
WKH\QHYHUFRQIOLFWZLWKDQ\RWKHUWUDQVDFWLRQ
$61$36+277$%/(67$%,/,7<WUDQVDFWLRQZLWK5($':5,7(DFFHVVLVJXDUDQWHHGWKDWLW
DORQHFDQXSGDWHWDEOHVEXWLWFRQIOLFWVZLWKDOORWKHUVLPXOWDQHRXVWUDQVDFWLRQVH[FHSWIRU
61$36+27DQG5($'&200,77('WUDQVDFWLRQVUXQQLQJLQ5($'21/<PRGH$
61$36+277$%/(67$%,/,7<WUDQVDFWLRQZLWK5($'21/<DFFHVVLVFRPSDWLEOHZLWKDQ\
RWKHUUHDGRQO\WUDQVDFWLRQEXWFRQIOLFWVZLWKDQ\WUDQVDFWLRQWKDWDWWHPSWVWRLQVHUWXSGDWH
RUGHOHWHGDWD

4 /RFNUHVROXWLRQ
7KHORFNUHVROXWLRQSDUDPHWHUGHWHUPLQHVZKDWKDSSHQVZKHQDWUDQVDFWLRQHQFRXQWHUVD
ORFNFRQIOLFW7KHUHDUHWZRRSWLRQV

50 INTERBASE 5
STARTING A NAMED TRANSACTION

g :$,7WKHGHIDXOWFDXVHVWKHWUDQVDFWLRQWRZDLWXQWLOORFNHGUHVRXUFHVDUHUHOHDVHG2QFHWKH
ORFNVDUHUHOHDVHGWKHWUDQVDFWLRQUHWULHVLWVRSHUDWLRQ
g 12:$,7UHWXUQVDORFNFRQIOLFWHUURUZLWKRXWZDLWLQJIRUORFNVWREHUHOHDVHG
%HFDXVH:$,7LVWKHGHIDXOWORFNUHVROXWLRQ\RXGRQ·WQHHGWRVSHFLI\LWLQD6(7
75$16$&7,21VWDWHPHQW)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVDUHHTXLYDOHQW7KH\ERWK
VWDUWDWUDQVDFWLRQWIRU5($':5,7(DFFHVV:$,7ORFNUHVROXWLRQDQG5($'
&200,77('LVRODWLRQOHYHO
EXEC SQL
SET TRANSACTION NAME t1 READ WRITE READ COMMITTED;
EXEC SQL
SET TRANSACTION NAME t1 READ WRITE WAIT READ COMMITTED;

7RXVH12:$,7WKHORFNUHVROXWLRQSDUDPHWHUPXVWEHVSHFLILHG)RUH[DPSOHWKHIROORZLQJ
VWDWHPHQWVWDUWVWKHQDPHGWUDQVDFWLRQWIRU5($':5,7(DFFHVV12:$,7ORFNUHVROXWLRQ
DQG61$36+27LVRODWLRQOHYHO
EXEC SQL
SET TRANSACTION NAME t1 READ WRITE NO WAIT READ SNAPSHOT;

:KHQORFNUHVROXWLRQLVVSHFLILHGLWIROORZVWKHRSWLRQDODFFHVVPRGHDQGSUHFHGHVWKH
RSWLRQDOLVRODWLRQOHYHOSDUDPHWHU

7,3 ,WLVJRRGSURJUDPPLQJSUDFWLFHWRVSHFLI\DWUDQVDFWLRQ·VORFNUHVROXWLRQHYHQZKHQLWLV
:$,7,WPDNHVDQDSSOLFDWLRQ·VVRXUFHFRGHHDVLHUWRUHDGDQGGHEXJEHFDXVHWKHSURJUDP·V
LQWHQWLRQVDUHFOHDUO\VSHOOHGRXW

4 5(6(59,1*FODXVH
7KHRSWLRQDO5(6(59,1*FODXVHHQDEOHVWUDQVDFWLRQVWRJXDUDQWHHWKHPVHOYHVVSHFLILFOHYHOV
RIDFFHVVWRDVXEVHWRIDYDLODEOHWDEOHVDWWKHH[SHQVHRIRWKHUVLPXOWDQHRXVWUDQVDFWLRQV
5HVHUYDWLRQWDNHVSODFHDWWKHVWDUWRIWKHWUDQVDFWLRQLQVWHDGRIRQO\ZKHQGDWDPDQLSXODWLRQ
VWDWHPHQWVUHTXLUHDSDUWLFXODUOHYHORIDFFHVV5(6(59,1*LVRQO\XVHIXOLQDQHQYLURQPHQW
ZKHUHVLPXOWDQHRXVWUDQVDFWLRQVVKDUHGDWDEDVHDFFHVV,WKDVWKUHHPDLQSXUSRVHV
g 7RSUHYHQWSRVVLEOHGHDGORFNVDQGXSGDWHFRQIOLFWVWKDWFDQRFFXULIORFNVDUHWDNHQRQO\
ZKHQDFWXDOO\QHHGHG WKHGHIDXOWEHKDYLRU 
g 7RSURYLGHIRUGHSHQGHQF\ORFNLQJWKHORFNLQJRIWDEOHVWKDWPD\EHDIIHFWHGE\WULJJHUVDQG
LQWHJULW\FRQVWUDLQWV:KLOHH[SOLFLWGHSHQGHQF\ORFNLQJLVQRWUHTXLUHGLWFDQDVVXUHWKDW
XSGDWHFRQIOLFWVGRQRWRFFXUEHFDXVHRILQGLUHFWWDEOHFRQIOLFWV
g 7RFKDQJHWKHOHYHORIVKDUHGDFFHVVIRURQHRUPRUHLQGLYLGXDOWDEOHVLQDWUDQVDFWLRQ)RU
H[DPSOHD5($':5,7(61$36+27WUDQVDFWLRQPD\QHHGH[FOXVLYHXSGDWHULJKWVIRUDVLQJOH
WDEOHDQGFRXOGXVHWKH5(6(59,1*FODXVHWRJXDUDQWHHLWVHOIVROHZULWHDFFHVVWRWKHWDEOH

PROGRAMMER’S GUIDE 51
CHAPTER 4 WORKING WITH TRANSACTIONS

,03257$17 $VLQJOH6(775$16$&7,21VWDWHPHQWFDQFRQWDLQHLWKHUD5(6(59,1*RUD86,1*FODXVH
EXWQRWERWK8VHWKH6(775$16$&7,21V\QWD[WRUHVHUYHWDEOHVIRUDWUDQVDFWLRQ
EXEC SQL
SET TRANSACTION [NAME name]
[READ WRITE| READ ONLY]
[WAIT | NO WAIT]
[[ISOLATION LEVEL] {SNAPSHOT [TABLE STABILITY]
| READ COMMITTED [[NO] RECORD_VERSION]}]
RESERVING <reserving_clause>;
<reserving_clause> = table [, table ...]
[FOR [SHARED | PROTECTED] {READ | WRITE}] [, <reserving_clause>]

(DFKWDEOHVKRXOGRQO\DSSHDURQFHLQWKH5(6(59,1*FODXVH(DFKWDEOHRUDOLVWRIWDEOHV
VHSDUDWHGE\FRPPDVPXVWEHIROORZHGE\DFODXVHGHVFULELQJWKHW\SHRIUHVHUYDWLRQ
UHTXHVWHG7KHIROORZLQJWDEOHOLVWVWKHVHUHVHUYDWLRQRSWLRQV

Reservation option Purpose


PROTECTED READ Prevents other transactions from updating rows. All transactions can select from
the table.
PROTECTED WRITE Prevents other transactions from updating rows.
SNAPSHOT and READ COMMITTED transactions can select from the table, but only
this transaction can update rows.
SHARED READ Any transaction can select from this table. Any READ WRITE transaction can update
this table. This is the most liberal reservation mode.
SHARED WRITE Any SNAPSHOT or READ COMMITTED READ WRITE transaction can update this table.
Other SNAPSHOT and READ COMMITTED transactions can also select from this table.
TABLE 4.7 Table reservation options for the RESERVING clause

7KHIROORZLQJVWDWHPHQWVWDUWVD61$36+27WUDQVDFWLRQWIRU5($':5,7(DFFHVVDQG
UHVHUYHVDVLQJOHWDEOHIRU3527(&7(':5,7(DFFHVV
EXEC SQL
SET TRANSACTION NAME t1 READ WRITE WAIT SNAPSHOT
RESERVING EMPLOYEE FOR PROTECTED WRITE;

7KHQH[WVWDWHPHQWVWDUWVD5($'&200,77('WUDQVDFWLRQWIRU5($':5,7(DFFHVVDQG
UHVHUYHVWZRWDEOHVRQHIRU6+$5(':5,7(DQGDQRWKHUIRU3527(&7('5($'
EXEC SQL
SET TRANSACTION NAME t1 READ WRITE WAIT READ COMMITTED
RESERVING EMPLOYEES FOR SHARED WRITE, EMP_PROJ
FOR PROTECTED READ;

52 INTERBASE 5
STARTING A NAMED TRANSACTION

61$36+27DQG5($'&200,77('WUDQVDFWLRQVXVH5(6(59,1*WRLPSOHPHQWPRUH
UHVWULFWLYHDFFHVVWRWDEOHVIRURWKHUVLPXOWDQHRXVWUDQVDFWLRQV61$36+277$%/(67$%,/,7<
WUDQVDFWLRQVXVH5(6(59,1*WRUHGXFHWKHOLNHOLKRRGRIGHDGORFNLQFULWLFDOVLWXDWLRQV

4 86,1*FODXVH
(YHU\WLPHDWUDQVDFWLRQLVVWDUWHG,QWHU%DVHUHVHUYHVV\VWHPUHVRXUFHVIRUHDFKGDWDEDVH
FXUUHQWO\DWWDFKHGIRUSURJUDPDFFHVV,QDPXOWLWUDQVDFWLRQPXOWLGDWDEDVHSURJUDPWKH
86,1*FODXVHFDQEHXVHGWRSUHVHUYHV\VWHPUHVRXUFHVE\UHVWULFWLQJWKHQXPEHURIRSHQ
GDWDEDVHVWRZKLFKDWUDQVDFWLRQKDVDFFHVV86,1*UHVWULFWVDWUDQVDFWLRQ·VDFFHVVWRWDEOHV
WRDOLVWHGVXEVHWRIDOORSHQGDWDEDVHVXVLQJWKHIROORZLQJV\QWD[
EXEC SQL
SET TRANSACTION [NAME name]
[READ WRITE | READ ONLY]
[WAIT | NO WAIT]
[[ISOLATION LEVEL] {SNAPSHOT [TABLE STABILITY]
| READ COMMITTED [[NO] RECORD_VERSION]}]
USING dbhandle> [, dbhandle ...];

,03257$17 $VLQJOH6(775$16$&7,21VWDWHPHQWFDQFRQWDLQHLWKHUD86,1*RUD5(6(59,1*FODXVH
EXWQRWERWK
7KHIROORZLQJ&SURJUDPIUDJPHQWRSHQVWKUHHGDWDEDVHVWHVWJGEUHVHDUFKJGEDQGHPSOR\HHJGE
DVVLJQLQJWKHPWRWKHGDWDEDVHKDQGOHV7(675(6($5&+DQG(03UHVSHFWLYHO\7KHQLW
VWDUWVWKHGHIDXOWWUDQVDFWLRQDQGUHVWULFWVLWVDFFHVVWR7(67DQG(03
. . .
EXEC SQL
SET DATABASE ATLAS = "test.gdb";
EXEC SQL
SET DATABASE RESEARCH = "research.gdb";
EXEC SQL
SET DATABASE EMP = "employee.gdb";
EXEC SQL
CONNECT TEST, RESEARCH, EMP; /* Open all databases */
EXEC SQL
SET TRANSACTION USING TEST, EMP;
. . .

PROGRAMMER’S GUIDE 53
CHAPTER 4 WORKING WITH TRANSACTIONS

Using transaction names in data statements


2QFHQDPHGWUDQVDFWLRQVDUHVWDUWHGXVHWKHLUQDPHVLQ,16(5783'$7('(/(7(DQG
23(1VWDWHPHQWVWRVSHFLI\ZKLFKWUDQVDFWLRQFRQWUROVWKHVWDWHPHQW)RUH[DPSOHWKH
IROORZLQJ&FRGHIUDJPHQWGHFODUHVWZRWUDQVDFWLRQKDQGOHVP\WUDQVDQGP\WUDQVLQLWLDOL]HV
WKHPWR]HURVWDUWVWKHWUDQVDFWLRQVDQGWKHQXVHVWKHWUDQVDFWLRQQDPHVWRTXDOLI\WKHGDWD
PDQLSXODWLRQVWDWHPHQWVWKDWIROORZ
. . .
EXEC SQL
BEGIN DECLARE SECTION;
long *mytrans1, *mytrans2;
char city[26];
EXEC SQL
END DECLARE SECTION;
mytrans1 = 0L;
mytrans2 = 0L;
. . .
EXEC SQL
SET DATABASE ATLAS = "atlas.gdb";
EXEC SQL
CONNECT;
EXEC SQL
DECLARE CITYLIST CURSOR FOR
SELECT CITY FROM CITIES
WHERE COUNTRY = "Mexico";
EXEC SQL
SET TRANSACTION NAME mytrans1;
EXEC SQL
SET TRANSACTION mytrans2 READ ONLY READ COMMITTED;
. . .
printf("Mexican city to add to database: ");
gets(city);
EXEC SQL
INSERT TRANSACTION mytrans1 INTO CITIES (CITY, COUNTRY)
VALUES :city, "Mexico";
EXEC SQL
COMMIT mytrans1;
EXEC SQL
OPEN TRANSACTION mytrans2 CITYLIST;
EXEC SQL
FETCH CITYLIST INTO :city;
while (!SQLCODE)

54 INTERBASE 5
ENDING A TRANSACTION

{
printf("%s\n", city);
EXEC SQL
FETCH CITYLIST INTO :city;
}
EXEC SQL
CLOSE CITYLIST;
EXEC SQL
COMMIT;
EXEC SQL
DISCONNECT;
. . .

$VWKLVH[DPSOHLOOXVWUDWHVDWUDQVDFWLRQQDPHFDQQRWDSSHDULQD'(&/$5(&85625
VWDWHPHQW7RXVHDQDPHZLWKDFXUVRUGHFODUDWLRQLQFOXGHWKHWUDQVDFWLRQQDPHLQWKH
FXUVRU·V23(1VWDWHPHQW7KHWUDQVDFWLRQQDPHLVQRWUHTXLUHGLQVXEVHTXHQW)(7&+DQG
&/26(VWDWHPHQWVIRUWKDWFXUVRU
Note 7KH'64/(;(&87(DQG(;(&87(,00(',$7(VWDWHPHQWVDOVRVXSSRUWWUDQVDFWLRQ
QDPHV
)RUPRUHLQIRUPDWLRQDERXWXVLQJWUDQVDFWLRQQDPHVZLWKGDWDPDQLSXODWLRQVWDWHPHQWVVHH
&KDSWHU´:RUNLQJZLWK'DWDµ)RUPRUHLQIRUPDWLRQDERXWWUDQVDFWLRQQDPHVDQGWKH
&200,7VWDWHPHQWVHH´8VLQJ&200,7µRQSDJH )RUPRUHLQIRUPDWLRQDERXWXVLQJ
WUDQVDFWLRQQDPHVZLWK'64/VWDWHPHQWVVHH´:RUNLQJZLWKPXOWLSOHWUDQVDFWLRQVLQ
'64/µRQSDJH 

Ending a transaction
:KHQDWUDQVDFWLRQ·VWDVNVDUHFRPSOHWHRUDQHUURUSUHYHQWVDWUDQVDFWLRQIURPFRPSOHWLQJ
WKHWUDQVDFWLRQPXVWEHHQGHGWRVHWWKHGDWDEDVHWRDFRQVLVWHQWVWDWH7KHUHDUHWZR
VWDWHPHQWVWKDWHQGWUDQVDFWLRQV
g &200,7PDNHVDWUDQVDFWLRQ·VFKDQJHVSHUPDQHQWLQWKHGDWDEDVH,WVLJQDOVWKDWD
WUDQVDFWLRQFRPSOHWHGDOOLWVDFWLRQVVXFFHVVIXOO\
g 52//%$&.XQGRHVDWUDQVDFWLRQ·VFKDQJHVUHWXUQLQJWKHGDWDEDVHWRLWVSUHYLRXVVWDWH
EHIRUHWKHWUDQVDFWLRQVWDUWHG52//%$&.LVW\SLFDOO\XVHGZKHQRQHRUPRUHHUURUVRFFXU
WKDWSUHYHQWDWUDQVDFWLRQIURPFRPSOHWLQJVXFFHVVIXOO\
%RWK&200,7DQG52//%$&. FORVHWKHUHFRUGVWUHDPVDVVRFLDWHGZLWKWKHWUDQVDFWLRQ
UHLQLWLDOL]HWKHWUDQVDFWLRQQDPHWR]HURDQGUHOHDVHV\VWHPUHVRXUFHVDOORFDWHGIRUWKH
WUDQVDFWLRQ)UHHGV\VWHPUHVRXUFHVDUHDYDLODEOHIRUVXEVHTXHQWXVHE\DQ\DSSOLFDWLRQRU
SURJUDP

PROGRAMMER’S GUIDE 55
CHAPTER 4 WORKING WITH TRANSACTIONS

&200,7DQG52//%$&.KDYHDGGLWLRQDOEHQHILWV7KH\FOHDUO\LQGLFDWHSURJUDPORJLFDQG
LQWHQWLRQPDNHDSURJUDPHDVLHUWRXQGHUVWDQGDQGPRVWLPSRUWDQWO\DVVXUHWKDWD
WUDQVDFWLRQ·VFKDQJHVDUHKDQGOHGDVLQWHQGHGE\WKHSURJUDPPHU
52//%$&.LVIUHTXHQWO\XVHGLQVLGHHUURUKDQGOLQJURXWLQHVWRFOHDQXSWUDQVDFWLRQVZKHQ
HUURUVRFFXU,WFDQDOVREHXVHGWRUROOEDFNDSDUWLDOO\FRPSOHWHGWUDQVDFWLRQSULRUWRUHWU\LQJ
LWDQGLWFDQEHXVHGWRUHVWRUHDGDWDEDVHWRLWVSULRUVWDWHLIDSURJUDPHQFRXQWHUVDQ
XQUHFRYHUDEOHHUURU

,03257$17 ,IWKHSURJUDPHQGVEHIRUHDWUDQVDFWLRQHQGVDWUDQVDFWLRQLVDXWRPDWLFDOO\UROOHGEDFNEXW
GDWDEDVHVDUHQRWFORVHG,IDSURJUDPHQGVZLWKRXWFORVLQJWKHGDWDEDVHGDWDORVVRU
FRUUXSWLRQLVSRVVLEOH7KHUHIRUHRSHQGDWDEDVHVVKRXOGDOZD\VEHFORVHGE\LVVXLQJH[SOLFLW
',6&211(&7&200,75(/($6(RU52//%$&.5(/($6(VWDWHPHQWV
)RUPRUHLQIRUPDWLRQDERXW',6&211(&7&200,75(/($6(DQG52//%$&.5(/($6(
VHH&KDSWHU´:RUNLQJZLWK'DWDEDVHVµ

Using COMMIT
8VH&200,7WRZULWHWUDQVDFWLRQFKDQJHVSHUPDQHQWO\WRDGDWDEDVH
&200,7FORVHVWKHUHFRUGVWUHDPVDVVRFLDWHGZLWKWKHWUDQVDFWLRQUHVHWVWKHWUDQVDFWLRQ
QDPHWR]HURDQGIUHHVV\VWHPUHVRXUFHVDVVLJQHGWRWKHWUDQVDFWLRQIRURWKHUXVHV7KH
FRPSOHWHV\QWD[IRU&200,7LV
EXEC SQL
COMMIT [TRANSACTION name] [RETAIN [SNAPSHOT] | RELEASE dbhandle
[, dbhandle ...]]

)RUH[DPSOHWKHIROORZLQJ&FRGHIUDJPHQWFRQWDLQVDFRPSOHWHWUDQVDFWLRQ,WJLYHVDOO
HPSOR\HHVZKRKDYHZRUNHGVLQFH'HFHPEHUDFRVWRIOLYLQJVDODU\LQFUHDVH
,IDOOTXDOLILHGHPSOR\HHUHFRUGVDUHVXFFHVVIXOO\XSGDWHGWKHWUDQVDFWLRQLVFRPPLWWHGDQG
WKHFKDQJHVDUHDFWXDOO\DSSOLHGWRWKHGDWDEDVH
. . .
EXEC SQL
SET TRANSACTION SNAPSHOT TABLE STABILITY;
EXEC SQL
UPDATE EMPLOYEE
SET SALARY = SALARY * 1.043
WHERE HIRE_DATE < "1-JAN-1993";
EXEC SQL
COMMIT;
. . .

56 INTERBASE 5
ENDING A TRANSACTION

%\GHIDXOW&200,7DIIHFWVRQO\WKHGHIDXOWWUDQVDFWLRQJGVBBWUDQV7RFRPPLWDQRWKHU
WUDQVDFWLRQXVHLWVWUDQVDFWLRQQDPHDVDSDUDPHWHUWR&200,7

7,3 (YHQ5($'21/<WUDQVDFWLRQVWKDWGRQRWFKDQJHDGDWDEDVHVKRXOGEHHQGHGZLWKD
&200,7UDWKHUWKDQ52//%$&.7KHGDWDEDVHLVQRWFKDQJHGEXWWKHRYHUKHDGUHTXLUHGWR
VWDUWVXEVHTXHQWWUDQVDFWLRQVLVJUHDWO\UHGXFHG

4 6SHFLI\LQJWUDQVDFWLRQQDPHV
7RFRPPLWFKDQJHVIRUWUDQVDFWLRQVRWKHUWKDQWKHGHIDXOWWUDQVDFWLRQVSHFLI\DWUDQVDFWLRQ
QDPHDVD&200,7SDUDPHWHU)RUH[DPSOHWKHIROORZLQJ&FRGHIUDJPHQWVWDUWVWZR
WUDQVDFWLRQVXVLQJQDPHVDQGFRPPLWVWKHP
. . .
EXEC SQL
BEGIN DECLARE SECTION;
isc_tr_handle TR1, TR2;
EXEC SQL
END DECLARE SECTION;
TR1 = (isc_tr_handle) NULL;
TR2 = (isc_tr_handle) NULL;
. . .
EXEC SQL
SET TRANSACTION NAME TR1;
EXEC SQL
SET TRANSACTION NAME TR2;
. . .
/* do actual processsing here */
. . .
EXEC SQL
COMMIT TRANSACTION TR1;
EXEC SQL
COMMIT TRANSACTION TR2;
. . .

,03257$17 ,QPXOWLWUDQVDFWLRQSURJUDPVWUDQVDFWLRQQDPHVPXVWDOZD\VEHVSHFLILHGIRU&200,7
H[FHSWZKHQFRPPLWWLQJWKHGHIDXOWWUDQVDFWLRQ

PROGRAMMER’S GUIDE 57
CHAPTER 4 WORKING WITH TRANSACTIONS

4 &RPPLWWLQJZLWKRXWIUHHLQJDWUDQVDFWLRQ
7RZULWHWUDQVDFWLRQFKDQJHVWRWKHGDWDEDVHZLWKRXWUHOHDVLQJWKHFXUUHQWWUDQVDFWLRQ
VQDSVKRWXVHWKH5(7$,1RSWLRQZLWK&200,77KH&200,75(7$,1VWDWHPHQWFRPPLWV
\RXUZRUNDQGRSHQVDQHZWUDQVDFWLRQSUHVHUYLQJWKHROGWUDQVDFWLRQ·VVQDSVKRW,QDEXV\
PXOWLXVHUHQYLURQPHQWUHWDLQLQJWKHVQDSVKRWVSHHGVXSSURFHVVLQJDQGXVHVIHZHUV\VWHP
UHVRXUFHVWKDQFORVLQJDQGVWDUWLQJDQHZWUDQVDFWLRQIRUHDFKDFWLRQ7KHGLVDGYDQWDJHRI
XVLQJ&200,75(7$,1LVWKDW\RXGRQRWVHHWKHSHQGLQJWUDQVDFWLRQVRIRWKHUXVHUV
7KHV\QWD[IRUWKH5(7$,1RSWLRQLVDVIROORZV
EXEC SQL
COMMIT [TRANSACTION name] RETAIN [SNAPSHOT];

7,3 'HYHORSHUVZKRXVH%RUODQGWRROVVXFKDV'HOSKLXVHWKLVIHDWXUHE\VSHFLI\LQJ´VRIW
FRPPLWVµLQWKH%'(FRQILJXUDWLRQ
)RUH[DPSOHWKHIROORZLQJ&FRGHIUDJPHQWXSGDWHVWKH3238/$7,21FROXPQE\
XVHUVSHFLILHGDPRXQWVIRUFLWLHVLQWKH&,7,(6WDEOHWKDWDUHLQDFRXQWU\DOVRVSHFLILHGE\WKH
XVHU(DFKWLPHDTXDOLILHGURZLVXSGDWHGD&200,7ZLWKWKH5(7$,1RSWLRQLVLVVXHG
SUHVHUYLQJWKHFXUUHQWFXUVRUVWDWXVDQGV\VWHPUHVRXUFHV
. . .
EXEC SQL
BEGIN DECLARE SECTION;
char country[26], city[26], asciimult[10];
int multiplier;
long pop;
EXEC SQL
END DECLARE SECTION;
. . .
main ()
{
EXEC SQL
DECLARE CHANGEPOP CURSOR FOR
SELECT CITY, POPULATION
FROM CITIES
WHERE COUNTRY = :country;
printf("Enter country with city populations needing adjustment: ");
gets(country);
EXEC SQL
SET TRANSACTION;
EXEC SQL
OPEN CHANGEPOP;
EXEC SQL
FETCH CHANGEPOP INTO :city, :pop;

58 INTERBASE 5
ENDING A TRANSACTION

while(!SQLCODE)
{
printf("City: %s Population: %ld\n", city, pop);
printf("\nPercent change (100%% to -100%%:");
gets(asciimult);
multiplier = atoi(asciimult);
EXEC SQL
UPDATE CITIES
SET POPULATION = POPULATION * (1 + :multiplier / 100)
WHERE CURRENT OF CHANGEPOP;
EXEC SQL
COMMIT RETAIN; /* commit changes, save current state */
EXEC SQL
FETCH CHANGEPOP INTO :city, :pop;
if (SQLCODE && (SQLCODE != 100))
{
isc_print_sqlerror(SQLCODE, isc_$status);
EXEC SQL
ROLLBACK;
EXEC SQL
DISCONNECT;
exit(1);
}
}
EXEC SQL
COMMIT;
EXEC SQL
DISCONNECT;
}

Note ,I\RXH[HFXWHD52//%$&.DIWHUD&200,75(7$,1LWUROOVEDFNRQO\XSGDWHVDQG
ZULWHVWKDWRFFXUUHGDIWHUWKH&200,75(7$,1

,03257$17 ,QPXOWLWUDQVDFWLRQSURJUDPVDWUDQVDFWLRQQDPHPXVWEHVSHFLILHGIRU&200,75(7$,1
H[FHSWZKHQUHWDLQLQJWKHVWDWHRIWKHGHIDXOWWUDQVDFWLRQ)RUPRUHLQIRUPDWLRQDERXW
WUDQVDFWLRQQDPHVVHH´1DPLQJWUDQVDFWLRQVµRQSDJH 

PROGRAMMER’S GUIDE 59
CHAPTER 4 WORKING WITH TRANSACTIONS

Using ROLLBACK
8VH52//%$&.WRUHVWRUHWKHGDWDEDVHWRLWVFRQGLWLRQSULRUWRWKHVWDUWRIWKHWUDQVDFWLRQ
52//%$&.DOVRFORVHVWKHUHFRUGVWUHDPVDVVRFLDWHGZLWKWKHWUDQVDFWLRQUHVHWVWKH
WUDQVDFWLRQQDPHWR]HURDQGIUHHVV\VWHPUHVRXUFHVDVVLJQHGWRWKHWUDQVDFWLRQIRURWKHU
XVHV52//%$&.W\SLFDOO\DSSHDUVLQHUURUKDQGOLQJURXWLQHV7KHV\QWD[IRU52//%$&.LV
EXEC SQL
ROLLBACK [TRANSACTION name] [RELEASE [dbhandle [, dbhandle ...]]];

)RUH[DPSOHWKHIROORZLQJ&FRGHIUDJPHQWFRQWDLQVDFRPSOHWHWUDQVDFWLRQWKDWJLYHVDOO
HPSOR\HHVZKRKDYHZRUNHGVLQFH'HFHPEHUDFRVWRIOLYLQJVDODU\
DGMXVWPHQW,IDOOTXDOLILHGHPSOR\HHUHFRUGVDUHVXFFHVVIXOO\XSGDWHGWKHWUDQVDFWLRQLV
FRPPLWWHGDQGWKHFKDQJHVDUHDFWXDOO\DSSOLHGWRWKHGDWDEDVH,IDQHUURURFFXUVDOO
FKDQJHVPDGHE\WKHWUDQVDFWLRQDUHXQGRQHDQGWKHGDWDEDVHLVUHVWRUHGWRLWVFRQGLWLRQ
SULRUWRWKHVWDUWRIWKHWUDQVDFWLRQ
. . .
EXEC SQL
SET TRANSACTION SNAPSHOT TABLE STABILITY;
EXEC SQL
UPDATE EMPLOYEES
SET SALARY = SALARY * 1.043
WHERE HIRE_DATE < "1-JAN-1993";
if (SQLCODE && (SQLCODE != 100))
{
isc_print_sqlerror(SQLCODE, isc_$status);
EXEC SQL
ROLLBACK;
EXEC SQL
DISCONNECT;
exit(1);
}
EXEC SQL
COMMIT;
EXEC SQL
DISCONNECT;
. . .

%\GHIDXOW 52//%$&.DIIHFWVRQO\WKHGHIDXOWWUDQVDFWLRQJGVBBWUDQV7RUROOEDFNRWKHU
WUDQVDFWLRQVXVHWKHLUWUDQVDFWLRQQDPHVDVSDUDPHWHUVWR
52//%$&.

60 INTERBASE 5
WORKING WITH MULTIPLE TRANSACTIONS

Working with multiple transactions


%HFDXVH,QWHU%DVHSURYLGHVVXSSRUWIRUWUDQVDFWLRQQDPHVDSURJUDPFDQXVHDVPDQ\
WUDQVDFWLRQVDWRQFHDVQHFHVVDU\WRFDUU\RXWLWVZRUN(DFKVLPXOWDQHRXVWUDQVDFWLRQLQD
SURJUDPUHTXLUHVLWVRZQQDPH$WUDQVDFWLRQ·VQDPHGLVWLQJXLVKHVLWIURPRWKHUDFWLYH
WUDQVDFWLRQV7KHQDPHFDQDOVREHXVHGLQGDWDPDQLSXODWLRQDQGWUDQVDFWLRQPDQDJHPHQW
VWDWHPHQWVWRVSHFLI\ZKLFKWUDQVDFWLRQFRQWUROVWKHVWDWHPHQW)RUPRUHLQIRUPDWLRQDERXW
GHFODULQJDQGXVLQJWUDQVDFWLRQQDPHVVHH´6WDUWLQJDQDPHGWUDQVDFWLRQµRQSDJH 
7KHUHDUHIRXUVWHSVIRUXVLQJQDPHGWUDQVDFWLRQVLQDSURJUDP
 'HFODUHDXQLTXHKRVWODQJXDJHYDULDEOHIRUHDFKWUDQVDFWLRQQDPH
 ,QLWLDOL]HHDFKWUDQVDFWLRQYDULDEOHWR]HUR
 8VH6(775$16$&7,21WRVWDUWHDFKWUDQVDFWLRQXVLQJDQDYDLODEOHWUDQVDFWLRQ
QDPH
 8VHWKHWUDQVDFWLRQQDPHVDVSDUDPHWHUVLQVXEVHTXHQWWUDQVDFWLRQPDQDJHPHQW
DQGGDWDPDQLSXODWLRQVWDWHPHQWVWKDWVKRXOGEHFRQWUROOHGE\DVSHFLILHG
WUDQVDFWLRQ

The default transaction


,QPXOWLWUDQVDFWLRQSURJUDPVLWLVJRRGSURJUDPPLQJSUDFWLFHWRVXSSO\DWUDQVDFWLRQQDPH
IRUHYHU\WUDQVDFWLRQDSURJUDPGHILQHV2QHWUDQVDFWLRQLQDPXOWLWUDQVDFWLRQSURJUDPFDQ
EHWKHGHIDXOWWUDQVDFWLRQJGVBBWUDQV:KHQWKHGHIDXOWWUDQVDFWLRQLVXVHGLQ
PXOWLWUDQVDFWLRQSURJUDPVLWWRRVKRXOGEHVWDUWHGH[SOLFLWO\DQGUHIHUHQFHGE\QDPHLQ
GDWDPDQLSXODWLRQVWDWHPHQWV
,IWKHWUDQVDFWLRQQDPHLVRPLWWHGIURPDWUDQVDFWLRQPDQDJHPHQWRUGDWDPDQLSXODWLRQ
VWDWHPHQW,QWHU%DVHDVVXPHVWKHVWDWHPHQWDIIHFWVWKHGHIDXOWWUDQVDFWLRQ,IWKHGHIDXOW
WUDQVDFWLRQKDVQRWEHHQH[SOLFLWO\VWDUWHGZLWKD6(775$16$&7,21VWDWHPHQWgpreLQVHUWV
DVWDWHPHQWGXULQJSUHSURFHVVLQJWRVWDUWLW

,03257$17 '64/SURJUDPVPXVWEHSUHSURFHVVHGZLWKWKHgpre -mVZLWFK,QWKLVPRGHgpreGRHV


QRWJHQHUDWHWKHGHIDXOWWUDQVDFWLRQDXWRPDWLFDOO\EXWLQVWHDGUHSRUWVDQHUURU'64/
SURJUDPVUHTXLUHWKDWDOOWUDQVDFWLRQVEHH[SOLFLWO\VWDUWHG

PROGRAMMER’S GUIDE 61
CHAPTER 4 WORKING WITH TRANSACTIONS

Using cursors
'(&/$5(&85625GRHVQRWVXSSRUWWUDQVDFWLRQQDPHV,QVWHDGWRDVVRFLDWHDQDPHG
WUDQVDFWLRQZLWKDFXUVRULQFOXGHWKHWUDQVDFWLRQQDPHDVDQRSWLRQDOSDUDPHWHULQWKH
FXUVRU·V23(1VWDWHPHQW$FXUVRUFDQRQO\EHDVVRFLDWHGZLWKDVLQJOHWUDQVDFWLRQ)RU
H[DPSOHWKHIROORZLQJVWDWHPHQWVGHFODUHDFXUVRUDQGRSHQLWDVVRFLDWLQJLWZLWKWKH
WUDQVDFWLRQW
. . .
EXEC SQL
DECLARE S CURSOR FOR
SELECT COUNTRY, CUST_NO, SUM(QTY_ORDERED)
FROM SALES
GROUP BY CUST_NO
WHERE COUNTRY = "Mexico";
EXEC SQL
SET TRANSACTION t1 READ ONLY READ COMMITTED;
. . .
EXEC SQL
OPEN TRANSACTION t1 S;
. . .

$Q23(1VWDWHPHQWZLWKRXWWKHRSWLRQDOWUDQVDFWLRQQDPHSDUDPHWHURSHUDWHVXQGHU
FRQWURORIWKHGHIDXOWWUDQVDFWLRQJGVBBWUDQV
2QFHDQDPHGWUDQVDFWLRQLVDVVRFLDWHGZLWKDFXUVRUVXEVHTXHQWFXUVRUVWDWHPHQWV
DXWRPDWLFDOO\RSHUDWHXQGHUFRQWURORIWKDWWUDQVDFWLRQ7KHUHIRUHLWGRHVQRWVXSSRUWD
WUDQVDFWLRQQDPHSDUDPHWHU)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVLOOXVWUDWHD)(7&+DQG
&/26(IRUWKH6FXUVRUDIWHULWLVDVVRFLDWHGZLWKWKHQDPHGWUDQVDFWLRQW
. . .
EXEC SQL
OPEN TRANSACTION t2 S;
EXEC SQL
FETCH S INTO :country, :cust_no, :qty;
while (!SQLCODE)
{
printf("%s %d %d\n", country, cust_no, qty);
EXEC SQL
FETCH S INTO :country, :cust_no, :qty;
}
EXEC SQL
CLOSE S;
. . .

62 INTERBASE 5
WORKING WITH MULTIPLE TRANSACTIONS

0XOWLSOHFXUVRUVFDQEHFRQWUROOHGE\DVLQJOHWUDQVDFWLRQRUHDFKWUDQVDFWLRQFDQFRQWUROD
VLQJOHFXUVRUDFFRUGLQJWRDSURJUDP·VQHHGV

A multi-transaction example
7KHIROORZLQJ&FRGHLOOXVWUDWHVWKHVWHSVUHTXLUHGWRFUHDWHDVLPSOHPXOWLWUDQVDFWLRQ
SURJUDP,WGHFODUHVWZRWUDQVDFWLRQKDQGOHVP\WUDQVDQGP\WUDQVLQLWLDOL]HVWKHPWR]HUR
VWDUWVWKHWUDQVDFWLRQVDQGWKHQXVHVWKHWUDQVDFWLRQQDPHVWRTXDOLI\WKHGDWDPDQLSXODWLRQ
VWDWHPHQWVWKDWIROORZ,WDOVRLOOXVWUDWHVWKHXVHRIDFXUVRUZLWKDQDPHGWUDQVDFWLRQ
. . .
EXEC SQL
BEGIN DECLARE SECTION;
long *mytrans1 = 0L, *mytrans2 = 0L;
char city[26];
EXEC SQL
END DECLARE SECTION;
. . .
EXEC SQL
DECLARE CITYLIST CURSOR FOR
SELECT CITY FROM CITIES
WHERE COUNTRY = "Mexico";
EXEC SQL
SET TRANSACTION NAME mytrans1;
EXEC SQL
SET TRANSACTION mytrans2 READ ONLY READ COMMITTED;
. . .
printf("Mexican city to add to database: ");
gets(city);
EXEC SQL
INSERT TRANSACTION mytrans1 INTO CITIES
VALUES :city, "Mexico", NULL, NULL, NULL, NULL;
EXEC SQL
COMMIT mytrans1;
EXEC SQL
OPEN TRANSACTION mytrans2 CITYLIST;
EXEC SQL
FETCH CITYLIST INTO :city;
while (!SQLCODE)
{
printf("%s\n", city);
EXEC SQL

PROGRAMMER’S GUIDE 63
CHAPTER 4 WORKING WITH TRANSACTIONS

FETCH CITYLIST INTO :city;


}
EXEC SQL
CLOSE CITYLIST;
EXEC SQL
COMMIT mytrans2;
EXEC SQL
DISCONNECT
. . .

Working with multiple transactions in DSQL


,Q,QWHU%DVH'64/DSSOLFDWLRQVFDQDOVRXVHPXOWLSOHWUDQVDFWLRQVEXWZLWKWKHIROORZLQJ
OLPLWDWLRQV
g 3URJUDPVPXVWEHSUHSURFHVVHGZLWKWKHgpre PVZLWFK
g 7UDQVDFWLRQQDPHVPXVWEHGHFODUHGVWDWLFDOO\7KH\FDQQRWEHGHILQHGWKURXJK
XVHUPRGLILHGKRVWYDULDEOHVDWUXQWLPH
g 7UDQVDFWLRQQDPHVPXVWEHLQLWLDOL]HGWR]HUREHIRUHDSSHDULQJLQ'64/VWDWHPHQWV
g $OOWUDQVDFWLRQVPXVWEHVWDUWHGZLWKH[SOLFLW6(775$16$&7,21
VWDWHPHQWV
g 1RGDWDGHILQLWLRQODQJXDJH ''/ FDQEHXVHGLQWKHFRQWH[WRIDQDPHGWUDQVDFWLRQLQDQ
HPEHGGHGSURJUDP''/PXVWDOZD\VRFFXULQWKHFRQWH[WRIWKHGHIDXOWWUDQVDFWLRQ
JGVBBWUDQV
g $VORQJDVDWUDQVDFWLRQQDPHSDUDPHWHULVQRWVSHFLILHGZLWKD6(775$16$&7,21
VWDWHPHQWLWFDQIROORZD35(3$5(VWDWHPHQWWRPRGLI\WKHEHKDYLRURIDVXEVHTXHQWO\
QDPHGWUDQVDFWLRQLQDQ(;(&87(RU(;(&87(,00(',$7(VWDWHPHQW7KLVHQDEOHVDXVHU
WRPRGLI\WUDQVDFWLRQEHKDYLRUVDWUXQWLPH
7UDQVDFWLRQQDPHVDUHIL[HGIRUDOO,QWHU%DVHSURJUDPVGXULQJSUHSURFHVVLQJDQGFDQQRWEH
G\QDPLFDOO\DVVLJQHG$XVHUFDQVWLOOPRGLI\'64/WUDQVDFWLRQEHKDYLRUDWUXQWLPH,WLVXS
WRWKHSURJUDPPHUWRDQWLFLSDWHSRVVLEOHWUDQVDFWLRQEHKDYLRUPRGLILFDWLRQDQGSODQIRULW
7KHIROORZLQJVHFWLRQGHVFULEHVKRZXVHUVFDQPRGLI\WUDQVDFWLRQEHKDYLRU

64 INTERBASE 5
WORKING WITH MULTIPLE TRANSACTIONS IN DSQL

Modifying transaction behavior with “?”


7KHQXPEHUDQGQDPHRIWUDQVDFWLRQVDYDLODEOHWRD'64/SURJUDPLVIL[HGZKHQWKH
SURJUDPLVSUHSURFHVVHGZLWKgpreWKH,QWHU%DVHSUHSURFHVVRU7KHSURJUDPPHU
GHWHUPLQHVERWKWKHQDPHGWUDQVDFWLRQVWKDWFRQWUROHDFK'64/VWDWHPHQWLQDSURJUDP
DQGWKHGHIDXOWEHKDYLRURIWKRVHWUDQVDFWLRQV$XVHUFDQFKDQJHDQDPHGWUDQVDFWLRQ·V
EHKDYLRUDWUXQWLPH
,Q'64/SURJUDPVDXVHUHQWHUVDQ64/VWDWHPHQWLQWRDKRVWODQJXDJHVWULQJYDULDEOHDQG
WKHQWKHKRVWYDULDEOHLVSURFHVVHGLQD35(3$5(VWDWHPHQWRU(;(&87(,00(',$7(
VWDWHPHQW

PREPARE
g &KHFNVWKHVWDWHPHQWLQWKHYDULDEOHIRUHUURUV
g /RDGVWKHVWDWHPHQWLQWRDQ;64/"'$IRUDVXEVHTXHQW(;(&87(VWDWHPHQW

EXECUTE IMMEDIATE
g &KHFNVWKHVWDWHPHQWIRUHUURUV
g /RDGVWKHVWDWHPHQWLQWRWKH;64/'$
g ([HFXWHVWKHVWDWHPHQW
%RWK(;(&87(DQG(;(&87(,00(',$7(RSHUDWHZLWKLQWKHFRQWH[WRID
SURJUDPPHUVSHFLILHGWUDQVDFWLRQZKLFKFDQEHDQDPHGWUDQVDFWLRQ,IWKHWUDQVDFWLRQ
QDPHLVRPLWWHGWKHVHVWDWHPHQWVDUHFRQWUROOHGE\WKHGHIDXOWWUDQVDFWLRQJGVBBWUDQV
<RXFDQPRGLI\WKHWUDQVDFWLRQEHKDYLRUIRUDQ(;(&87(DQG(;(&87(,00(',$7(
VWDWHPHQWE\
g (QDEOLQJDXVHUWRHQWHUD6(775$16$&7,21VWDWHPHQWLQWRDKRVWYDULDEOH
g ([HFXWLQJWKH6(775$16$&7,21VWDWHPHQWEHIRUHWKH(;(&87(RU(;(&87(
,00(',$7(ZKRVHWUDQVDFWLRQFRQWH[WVKRXOGEHPRGLILHG
,QWKLVFRQWH[WD6(775$16$&7,21VWDWHPHQWFKDQJHVWKHEHKDYLRURIWKHQH[WQDPHGRU
GHIDXOWWUDQVDFWLRQXQWLODQRWKHU6(775$16$&7,21RFFXUV
7KHIROORZLQJ&FRGHIUDJPHQWSURYLGHVWKHXVHUWKHRSWLRQRIVSHFLI\LQJDQHZWUDQVDFWLRQ
EHKDYLRUDSSOLHVWKHEHKDYLRUFKDQJHH[HFXWHVWKHQH[WXVHUVWDWHPHQWLQWKHFRQWH[WRIWKDW
FKDQJHGWUDQVDFWLRQWKHQUHVWRUHVWKHWUDQVDFWLRQ·VRULJLQDOEHKDYLRU
. . .
EXEC SQL
BEGIN DECLARE SECTION;
char usertrans[512], query[1024];

PROGRAMMER’S GUIDE 65
CHAPTER 4 WORKING WITH TRANSACTIONS

char deftrans[] = {"SET TRANSACTION READ WRITE WAIT SNAPSHOT"};


EXEC SQL
END DECLARE SECTION;
. . .
printf("\nEnter SQL statement: ");
gets(query);
printf("\nChange transaction behavior (Y/N)? ");
gets(usertrans);
if (usertrans[0] == "Y" || usertrans[0] == "y")
{
printf("\nEnter \"SET TRANSACTION\" and desired behavior: ");
gets(usertrans);
EXEC SQL
COMMIT usertrans;
EXEC SQL
EXECUTE IMMEDIATE usertrans;
}
else
{
EXEC SQL
EXECUTE IMMEDIATE deftrans;
}
EXEC SQL
EXECUTE IMMEDIATE query;
EXEC SQL
EXECUTE IMMEDIATE deftrans;
. . .

,03257$17 $VWKLVH[DPSOHLOOXVWUDWHV\RXPXVWFRPPLWRUUROOEDFNDQ\SUHYLRXVWUDQVDFWLRQVEHIRUH
\RXFDQH[HFXWH6(775$16$&7,21

66 INTERBASE 5
CHAPTER

Working with Data


Chapter5
5
Definition Statements

7KLVFKDSWHUGLVFXVVHVKRZWRFUHDWHPRGLI\DQGGHOHWHGDWDEDVHVWDEOHVYLHZVDQGLQGH[HV
LQ64/DSSOLFDWLRQV$GDWDEDVH·VWDEOHVYLHZVDQGLQGH[HVPDNHXSPRVWRILWVXQGHUO\LQJ
VWUXFWXUHRUPHWDGDWD

,03257$17 7KHGLVFXVVLRQLQWKLVFKDSWHUDSSOLHVHTXDOO\WRG\QDPLF64/ '64/ DSSOLFDWLRQVH[FHSW


WKDWXVHUVHQWHU'64/GDWDGHILQLWLRQVWDWHPHQWVDWUXQWLPHDQGGRQRWSUHIDFHWKRVH
VWDWHPHQWVZLWK(;(&64/

67
CHAPTER 5 WORKING WITH DATA DEFINITION STATEMENTS

7KHSUHIHUUHGPHWKRGIRUFUHDWLQJPRGLI\LQJDQGGHOHWLQJPHWDGDWDLVWKURXJKWKH
,QWHU%DVHLQWHUDFWLYH64/WRROisqlEXWLQVRPHLQVWDQFHVLWPD\EHQHFHVVDU\RUGHVLUDEOH
WRHPEHGVRPHGDWDGHILQLWLRQFDSDELOLWLHVLQDQ64/DSSOLFDWLRQ%RWK64/DQG'64/
DSSOLFDWLRQVFDQXVHWKHIROORZLQJVXEVHWRIGDWDGHILQLWLRQVWDWHPHQWV

CREATE statement ALTER statement DROP statement


CREATE DATABASE ALTER DATABASE —

CREATE DOMAIN ALTER DOMAIN DROP DOMAIN

CREATE GENERATOR SET GENERATOR —

CREATE INDEX ALTER INDEX DROP INDEX

CREATE SHADOW ALTER SHADOW DROP SHADOW

CREATE TABLE ALTER TABLE DROP TABLE

CREATE VIEW — DROP VIEW

DECLARE EXTERNAL — DROP EXTERNAL

DECLARE FILTER — DROP FILTER

TABLE 5.1 Data definition statements supported for embedded applications

'64/DOVRVXSSRUWVFUHDWLQJDOWHULQJDQGGURSSLQJVWRUHGSURFHGXUHVWULJJHUVDQG
H[FHSWLRQV'64/LVHVSHFLDOO\SRZHUIXOIRUGDWDGHILQLWLRQEHFDXVHLWHQDEOHVXVHUVWRHQWHU
DQ\VXSSRUWHGGDWDGHILQLWLRQVWDWHPHQWDWUXQWLPH)RUH[DPSOHisqlLWVHOILVD'64/
DSSOLFDWLRQ)RUPRUHLQIRUPDWLRQDERXWXVLQJisqlWRGHILQHVWRUHGSURFHGXUHVWULJJHUVDQG
H[FHSWLRQVVHHWKH'DWD'HILQLWLRQ*XLGH)RUDFRPSOHWHGLVFXVVLRQRI'64/SURJUDPPLQJ
VHH&KDSWHU´8VLQJ'\QDPLF64/µ

Creating metadata
64/GDWDGHILQLWLRQVWDWHPHQWVDUHXVHGLQDSSOLFDWLRQVWKHVROHSXUSRVHRIZKLFKLVWRFUHDWH
RUPRGLI\GDWDEDVHVRUWDEOHV7\SLFDOO\WKHH[SHFWDWLRQLVWKDWWKHVHDSSOLFDWLRQVZLOOEHXVHG
RQO\RQFHE\DQ\JLYHQXVHUWKHQGLVFDUGHGRUVDYHGIRUODWHUPRGLILFDWLRQE\DGDWDEDVH
GHVLJQHUZKRFDQUHDGWKHSURJUDPFRGHDVDUHFRUGRIDGDWDEDVH·VVWUXFWXUH,IGDWD
GHILQLWLRQFKDQJHVPXVWEHPDGHHGLWLQJDFRS\RIH[LVWLQJFRGHLVHDVLHUWKDQVWDUWLQJRYHU
Note 8VHWKH,QWHU%DVHLQWHUDFWLYH64/WRROisqlWRFUHDWHDQGDOWHUGDWDGHILQLWLRQV
ZKHQHYHUSRVVLEOH)RUPRUHLQIRUPDWLRQDERXWisqlVHHWKH2SHUDWLRQV*XLGH

68 INTERBASE 5
CREATING METADATA

7KH64/&5($7(VWDWHPHQWLVXVHGWRPDNHQHZGDWDEDVHVGRPDLQVWDEOHVYLHZVRU
LQGH[HV$&200,7VWDWHPHQWPXVWIROORZHYHU\&5($7(VRWKDWVXEVHTXHQW&5($7(
VWDWHPHQWVFDQXVHSUHYLRXVO\GHILQHGPHWDGDWDXSRQZKLFKWKH\PD\UHO\)RUH[DPSOH
GRPDLQGHILQLWLRQVPXVWEHFRPPLWWHGEHIRUHWKHGRPDLQFDQEHUHIHUHQFHGLQVXEVHTXHQW
WDEOHGHILQLWLRQV

,03257$17 $SSOLFDWLRQVWKDWPL[GDWDGHILQLWLRQDQGGDWDPDQLSXODWLRQPXVWEHSUHSURFHVVHGXVLQJWKH
gpre -mVZLWFK6XFKDSSOLFDWLRQVPXVWH[SOLFLWO\VWDUWHYHU\WUDQVDFWLRQZLWK6(7
75$16$&7,21

Creating a database
&5($7('$7$%$6(HVWDEOLVKHVDQHZGDWDEDVHDQGLWVV\VWHPWDEOHVWDEOHVWKDWGHVFULEHWKH
LQWHUQDOVWUXFWXUHRIWKHGDWDEDVH,QWHU%DVHXVHVWKHV\VWHPWDEOHVZKHQHYHUDQDSSOLFDWLRQ
DFFHVVHVDGDWDEDVH64/SURJUDPVFDQUHDGWKHGDWDLQPRVWRIWKHVHWDEOHVMXVWOLNHDQ\
XVHUFUHDWHGWDEOH
,QLWVPRVWHOHPHQWDU\IRUPWKHV\QWD[IRU&5($7('$7$%$6(LV
EXEC SQL
CREATE DATABASE "<filespec>";

&5($7('$7$%$6(PXVWDSSHDUEHIRUHDQ\RWKHU&5($7(VWDWHPHQWV,WUHTXLUHVRQH
SDUDPHWHUWKHQDPHRIDGDWDEDVHWRFUHDWH)RUH[DPSOHWKHIROORZLQJVWDWHPHQWFUHDWHVD
GDWDEDVHQDPHGHPSOR\HHJGE
EXEC SQL
CREATE DATABASE "employee.gdb";
Note 7KHGDWDEDVHQDPHFDQLQFOXGHDIXOOILOHVSHFLILFDWLRQLQFOXGLQJERWKKRVWRUQRGH
QDPHVDQGDGLUHFWRU\SDWKWRWKHORFDWLRQZKHUHWKHGDWDEDVHILOHVKRXOGEHFUHDWHG)RU
LQIRUPDWLRQDERXWILOHVSHFLILFDWLRQVIRUDSDUWLFXODURSHUDWLQJV\VWHPVHHWKHRSHUDWLQJ
V\VWHPPDQXDOV

,03257$17 $OWKRXJK,QWHU%DVHHQDEOHVDFFHVVWRUHPRWHGDWDEDVHVZKHQDGDWDEDVHLVFUHDWHGLW
VKRXOGRQO\EHFUHDWHGGLUHFWO\RQWKHPDFKLQHZKHUHLWLVWRUHVLGH

4 2SWLRQDOSDUDPHWHUV
7KHUHDUHRSWLRQDOSDUDPHWHUVIRU&5($7('$7$%$6()RUH[DPSOHZKHQDQDSSOLFDWLRQ
UXQQLQJRQDFOLHQWDWWHPSWVWRFRQQHFWWRDQ,QWHU%DVHVHUYHULQRUGHUWRFUHDWHDGDWDEDVH
LWPD\EHH[SHFWHGWRSURYLGH86(5DQG3$66:25'SDUDPHWHUVEHIRUHWKHFRQQHFWLRQLV
HVWDEOLVKHG2WKHUSDUDPHWHUVVSHFLI\WKHGDWDEDVHSDJHVL]HWKHQXPEHUDQGVL]HRI
PXOWLILOHGDWDEDVHVDQGWKHGHIDXOWFKDUDFWHUVHWIRUWKHGDWDEDVH

PROGRAMMER’S GUIDE 69
CHAPTER 5 WORKING WITH DATA DEFINITION STATEMENTS

)RUDFRPSOHWHGLVFXVVLRQRIDOO&5($7('$7$%$6(SDUDPHWHUVVHHWKH'DWD'HILQLWLRQ*XLGH
)RUWKHFRPSOHWHV\QWD[RI&5($7('$7$%$6(VHHWKH/DQJXDJH5HIHUHQFH

,03257$17 $QDSSOLFDWLRQWKDWFUHDWHVDGDWDEDVHPXVWEHSUHSURFHVVHGZLWKWKHgpre -mVZLWFK,W


PXVWDOVRFUHDWHDWOHDVWRQHWDEOH,IDGDWDEDVHLVFUHDWHGZLWKRXWDWDEOHLWFDQQRWEH
VXFFHVVIXOO\RSHQHGE\DQRWKHUSURJUDP$SSOLFDWLRQVWKDWSHUIRUPERWKGDWDGHILQLWLRQ
DQGGDWDPDQLSXODWLRQPXVWGHFODUHWDEOHVZLWK'(&/$5(7$%/(EHIRUHFUHDWLQJDQG
SRSXODWLQJWKHP)RUPRUHLQIRUPDWLRQDERXWWDEOHFUHDWLRQVHH´&UHDWLQJDWDEOHµRQ
SDJH 

4 6SHFLI\LQJDGHIDXOWFKDUDFWHUVHW
$GDWDEDVH·VGHIDXOWFKDUDFWHUVHWGHVLJQDWLRQVSHFLILHVWKHFKDUDFWHUVHWWKHVHUYHUXVHVWR
WUDQVOLWHUDWHDQGVWRUH&+$59$5&+$5DQGWH[W%OREGDWDLQWKHGDWDEDVHZKHQQRRWKHU
FKDUDFWHUVHWLQIRUPDWLRQLVSURYLGHG$GHIDXOWFKDUDFWHUVHWVKRXOGDOZD\VEHVSHFLILHGIRU
DGDWDEDVHZKHQLWLVFUHDWHGZLWK&5($7('$7$%$6(
7RVSHFLI\DGHIDXOWFKDUDFWHUVHWXVHWKH'()$8/7&+$5$&7(56(7FODXVHRI&5($7(
'$7$%$6()RUH[DPSOHWKHIROORZLQJVWDWHPHQWFUHDWHVDGDWDEDVHWKDWXVHVWKH,62B
FKDUDFWHUVHW
EXEC SQL
CREATE DATABASE "europe.gdb" DEFAULT CHARACTER SET ISO8859_1;

,I\RXGRQRWVSHFLI\DFKDUDFWHUVHWWKHFKDUDFWHUVHWGHIDXOWVWR121(8VLQJFKDUDFWHUVHW
121(PHDQVWKDWWKHUHLVQRFKDUDFWHUVHWDVVXPSWLRQIRUFROXPQVGDWDLVVWRUHGDQG
UHWULHYHGMXVWDV\RXRULJLQDOO\HQWHUHGLW<RXFDQORDGDQ\FKDUDFWHUVHWLQWRDFROXPQGHILQHG
ZLWK121(EXW\RXFDQQRWODWHUPRYHWKDWGDWDLQWRDQRWKHUFROXPQWKDWKDVEHHQGHILQHG
ZLWKDGLIIHUHQWFKDUDFWHUVHW,QWKLVFDVHQRWUDQVOLWHUDWLRQLVSHUIRUPHGEHWZHHQWKHVRXUFH
DQGGHVWLQDWLRQFKDUDFWHUVHWVDQGHUURUVPD\RFFXUGXULQJDVVLJQPHQW
)RUPRUHLQIRUPDWLRQDERXWVSHFLI\LQJDGHIDXOWFKDUDFWHUVHWIRUDGDWDEDVHVHH´6SHFLI\LQJ
DGHIDXOWFKDUDFWHUVHWµRQSDJH 
)RUDFRPSOHWHGHVFULSWLRQRIWKH'()$8/7&+$5$&7(56(7FODXVHDQGDOLVWRIWKH
FKDUDFWHUVHWVVXSSRUWHGE\,QWHU%DVHVHHWKH'DWD'HILQLWLRQ*XLGH

Creating a domain
&5($7('20$,1FUHDWHVDFROXPQGHILQLWLRQWKDWLVJOREDOWRWKHGDWDEDVHDQGWKDWFDQEH
XVHGWRGHILQHFROXPQVLQVXEVHTXHQW&5($7(7$%/(VWDWHPHQWV&5($7('20$,1LV
HVSHFLDOO\XVHIXOZKHQPDQ\WDEOHVLQDGDWDEDVHFRQWDLQLGHQWLFDOFROXPQGHILQLWLRQV)RU
H[DPSOHLQDQHPSOR\HHGDWDEDVHVHYHUDOWDEOHVPLJKWGHILQHFROXPQVIRUHPSOR\HHV·ILUVW
DQGODVWQDPHV

70 INTERBASE 5
CREATING METADATA

$WLWVVLPSOHVWWKHV\QWD[IRU&5($7('20$,1LV
EXEC SQL
CREATE DOMAIN name AS <datatype>;

7KHIROORZLQJVWDWHPHQWVFUHDWHWZRGRPDLQV),5671$0(DQG/$671$0(
EXEC SQL
CREATE DOMAIN FIRSTNAME AS VARCHAR(15);
EXEC SQL
CREATE DOMAIN LASTNAME AS VARCHAR(20);
EXEC SQL
COMMIT;

2QFHDGRPDLQLVGHILQHGDQGFRPPLWWHGLWFDQEHXVHGLQ&5($7(7$%/(VWDWHPHQWVWR
GHILQHFROXPQV)RUH[DPSOHWKHIROORZLQJ&5($7(7$%/(IUDJPHQWLOOXVWUDWHVKRZWKH
),5671$0(DQG/$671$0(GRPDLQVFDQEHXVHGLQSODFHRIFROXPQGHILQLWLRQVLQWKH
(03/2<((WDEOHGHILQLWLRQ
EXEC SQL
CREATE TABLE EMPLOYEE
(
. . .
FIRST_NAME FIRSTNAME NOT NULL,
LAST_NAME LASTNAME NOT NULL;
. . .
);

$GRPDLQGHILQLWLRQFDQDOVRVSHFLI\DGHIDXOWYDOXHD12718//DWWULEXWHD&+(&.
FRQVWUDLQWWKDWOLPLWVLQVHUWVDQGXSGDWHVWRDUDQJHRIYDOXHVDFKDUDFWHUVHWDQGDFROODWLRQ
RUGHU
)RUPRUHLQIRUPDWLRQDERXWFUHDWLQJGRPDLQVDQGXVLQJWKHPGXULQJWDEOHFUHDWLRQVHHWKH
'DWD'HILQLWLRQ*XLGH)RUWKHFRPSOHWHV\QWD[RI&5($7('20$,1VHHWKH/DQJXDJH5HIHUHQFH

Creating a table
7KH&5($7(7$%/(VWDWHPHQWGHILQHVDQHZGDWDEDVHWDEOHDQGWKHFROXPQVDQGLQWHJULW\
FRQVWUDLQWVZLWKLQWKDWWDEOH(DFKFROXPQFDQLQFOXGHDFKDUDFWHUVHWVSHFLILFDWLRQDQGD
FROODWLRQRUGHUVSHFLILFDWLRQ&5($7(7$%/(DOVRDXWRPDWLFDOO\LPSRVHVDGHIDXOW64/
VHFXULW\VFKHPHRQWKHWDEOH7KHSHUVRQZKRFUHDWHVDWDEOHEHFRPHVLWVRZQHU$WDEOH·V
RZQHULVDVVLJQHGDOOSULYLOHJHVIRULWLQFOXGLQJWKHULJKWWRJUDQWSULYLOHJHVWRRWKHUXVHUV
$WDEOHFDQEHFUHDWHGRQO\IRUDGDWDEDVHWKDWDOUHDG\H[LVWV$WLWVVLPSOHVWWKHV\QWD[IRU
&5($7(7$%/(LVDVIROORZV

PROGRAMMER’S GUIDE 71
CHAPTER 5 WORKING WITH DATA DEFINITION STATEMENTS

EXEC SQL
CREATE TABLE name (<col_def> | <table_constraint>
[, <col_def> | <table_constraint> ...]);

FROBGHI!GHILQHVDFROXPQXVLQJWKHIROORZLQJV\QWD[
col {<datatype> | COMPUTED [BY] (<expr>) | domain}
<col_constraint> COLLATE collation

FRO!PXVWEHDFROXPQQDPHXQLTXHZLWKLQWKHWDEOHGHILQLWLRQ
GDWDW\SH!VSHFLILHVWKH64/GDWDW\SHWRXVHIRUFROXPQHQWULHV&20387('%<FDQEHXVHG
WRGHILQHDFROXPQZKRVHYDOXHLVFRPSXWHGIURPDQH[SUHVVLRQZKHQWKHFROXPQLVDFFHVVHG
DWUXQWLPH
FROBFRQVWUDLQW!LVDQRSWLRQDOLQWHJULW\FRQVWUDLQWWRDSSO\WRDFROXPQWDEOHFRQVWUDLQWLVDQ
RSWLRQDOLQWHJULW\FRQVWUDLQWWRDSSO\WRDQHQWLUHWDEOH,QWHJULW\FRQVWUDLQWVDUHXVHGWR
HQVXUHGDWDHQWHUHGLQDWDEOHPHHWVVSHFLILFUHTXLUHPHQWVWRVSHFLI\WKDWGDWDHQWHUHGLQD
WDEOHRUFROXPQLVXQLTXHRUWRHQIRUFHUHIHUHQWLDOLQWHJULW\ZLWKRWKHUWDEOHVLQWKHGDWDEDVH
7KHIROORZLQJFRGHIUDJPHQWFRQWDLQV64/VWDWHPHQWVWKDWFUHDWHDGDWDEDVHHPSOR\HHJGEDQG
FUHDWHDWDEOH(03/2<((B352-(&7ZLWKWKUHHFROXPQV(03B12352-B,'DQG'87,(6
EXEC SQL
CREATE DATABASE "employee.gdb";
EXEC SQL
CREATE TABLE EMPLOYEE_PROJECT
(
EMP_NO SMALLINT NOT NULL,
PROJ_ID CHAR(5) NOT NULL,
DUTIES Blob SUBTYPE 1 SEGMENT SIZE 240
);
EXEC SQL
COMMIT;

$QDSSOLFDWLRQFDQFUHDWHPXOWLSOHWDEOHVEXWGXSOLFDWLQJDQH[LVWLQJWDEOHQDPHLVQRW
SHUPLWWHG
)RUPRUHLQIRUPDWLRQDERXW64/GDWDW\SHVDQGLQWHJULW\FRQVWUDLQWVVHHWKH'DWD'HILQLWLRQ
*XLGH)RUPRUHLQIRUPDWLRQDERXW&5($7(7$%/(V\QWD[VHHWKH/DQJXDJH5HIHUHQFH)RU
PRUHLQIRUPDWLRQDERXWFKDQJLQJRUDVVLJQLQJWDEOHSULYLOHJHVVHHWKHVHFXULW\FKDSWHULQWKH
'DWD'HILQLWLRQ*XLGH

4 &UHDWLQJDFRPSXWHGFROXPQ
$FRPSXWHGFROXPQLVRQHZKRVHYDOXHLVFDOFXODWHGZKHQWKHFROXPQLVDFFHVVHGDWUXQWLPH
7KHYDOXHFDQEHGHULYHGIURPDQ\YDOLG64/H[SUHVVLRQWKDWUHVXOWVLQDVLQJOHQRQDUUD\
YDOXH

72 INTERBASE 5
CREATING METADATA

7RFUHDWHDFRPSXWHGFROXPQXVHWKHIROORZLQJFROXPQGHFODUDWLRQV\QWD[LQ&5($7(
7$%/(
col COMPUTED [BY] (<expr>)

7KHH[SUHVVLRQFDQUHIHUHQFHSUHYLRXVO\GHILQHGFROXPQVLQWKHWDEOH)RUH[DPSOHWKH
IROORZLQJVWDWHPHQWFUHDWHVDFRPSXWHGFROXPQ)8//B1$0(E\FRQFDWHQDWLQJWZRRWKHU
FROXPQV/$67B1$0(DQG),567B1$0(
EXEC SQL
CREATE TABLE EMPLOYEE
(
. . .
FIRST_NAME VARCHAR(10) NOT NULL,
LAST_NAME VARCHAR(15) NOT NULL,
. . .
FULL_NAME COMPUTED BY (LAST_NAME || ", " || FIRST_NAME)
);

)RUPRUHLQIRUPDWLRQDERXW&20387('%<VHHWKH'DWD'HILQLWLRQ*XLGH

4 'HFODULQJDQGFUHDWLQJDWDEOH
,QSURJUDPVWKDWPL[GDWDGHILQLWLRQDQGGDWDPDQLSXODWLRQWKH'(&/$5(7$%/(VWDWHPHQW
PXVWEHXVHGWRGHVFULEHDWDEOH·VVWUXFWXUHWRWKH,QWHU%DVHSUHSURFHVVRUgpreEHIRUHWKDW
WDEOHFDQEHFUHDWHG'XULQJSUHSURFHVVLQJLIgpreHQFRXQWHUVD'(&/$5(7$%/(VWDWHPHQW
LWVWRUHVWKHWDEOH·VGHVFULSWLRQIRUODWHUUHIHUHQFH:KHQgpreHQFRXQWHUVD&5($7(7$%/(
VWDWHPHQWIRUWKHSUHYLRXVO\GHFODUHGWDEOHLWYHULILHVWKDWWKHFROXPQGHVFULSWLRQVLQWKH
&5($7(VWDWHPHQWPDWFKWKRVHLQWKH'(&/$5(VWDWHPHQW,IWKH\GRQRWPDWFKgpre
UHSRUWVWKHHUURUVDQGFDQFHOVSUHSURFHVVLQJVRWKDWWKHHUURUFDQEHIL[HG
:KHQXVHG'(&/$5(7$%/(PXVWFRPHEHIRUHWKH&5($7(7$%/(VWDWHPHQWLWGHVFULEHV
)RUH[DPSOHWKHIROORZLQJFRGHIUDJPHQWGHFODUHVDWDEOH
(03/2<((B352-WKHQFUHDWHVLW
EXEC SQL
DECLARE EMPLOYEE_PROJECT TABLE
(
EMP_NO SMALLINT,
PROJ_ID CHAR(5),
DUTIES Blob(240, 1)
);
EXEC SQL
CREATE TABLE EMPLOYEE_PROJECT
(
EMP_NO SMALLINT,
PROJ_ID CHAR(5),

PROGRAMMER’S GUIDE 73
CHAPTER 5 WORKING WITH DATA DEFINITION STATEMENTS

DUTIES Blob(240, 1)
);
EXEC SQL
COMMIT;

)RUPRUHLQIRUPDWLRQDERXW'(&/$5(7$%/(VHHWKH/DQJXDJH5HIHUHQFH

Creating a view
$YLHZLVDYLUWXDOWDEOHWKDWLVEDVHGRQDVXEVHWRIRQHRUPRUHDFWXDOWDEOHVLQDGDWDEDVH
9LHZVDUHXVHGWR
g 5HVWULFWXVHUDFFHVVWRGDWDE\SUHVHQWLQJRQO\DVXEVHWRIDYDLODEOHGDWD
g 5HDUUDQJHDQGSUHVHQWGDWDIURPWZRRUPRUHWDEOHVLQDPDQQHUHVSHFLDOO\XVHIXOWRWKH
SURJUDP
8QOLNHDWDEOHDYLHZLVQRWVWRUHGLQWKHGDWDEDVHDVUDZGDWD,QVWHDGZKHQDYLHZLVFUHDWHG
WKHGHILQLWLRQRIWKHYLHZLVVWRUHGLQWKHGDWDEDVH:KHQDSURJUDPXVHVWKHYLHZ,QWHU%DVH
UHDGVWKHYLHZGHILQLWLRQDQGTXLFNO\JHQHUDWHVWKHRXWSXWDVLILWZHUHDWDEOH
7RPDNHDYLHZXVHWKHIROORZLQJ&5($7(9,(:V\QWD[
EXEC SQL
CREATE VIEW name [(view_col [, view_col ...)] AS
<select> [WITH CHECK OPTION];

7KHQDPHRIWKHYLHZQDPHPXVWEHXQLTXHZLWKLQWKHGDWDEDVH
7RJLYHHDFKFROXPQGLVSOD\HGLQWKHYLHZLWVRZQQDPHLQGHSHQGHQWRILWVFROXPQQDPHLQ
DQXQGHUO\LQJWDEOHHQFORVHDOLVWRIYLHZBFROSDUDPHWHUVLQSDUHQWKHVHV(DFKFROXPQRIGDWD
UHWXUQHGE\WKHYLHZ·V6(/(&7VWDWHPHQWLVDVVLJQHGVHTXHQWLDOO\WRDFRUUHVSRQGLQJYLHZ
FROXPQQDPH,IDOLVWRIYLHZFROXPQQDPHVLVRPLWWHGFROXPQQDPHVDUHDVVLJQHGGLUHFWO\
IURPWKHXQGHUO\LQJWDEOH
/LVWLQJLQGHSHQGHQWQDPHVIRUFROXPQVLQDYLHZHQVXUHVWKDWWKHDSSHDUDQFHRIDYLHZGRHV
QRWFKDQJHLILWVXQGHUO\LQJWDEOHVWUXFWXUHVDUHPRGLILHG
Note $YLHZFROXPQQDPHPXVWEHSURYLGHGIRUHDFKFROXPQRIGDWDUHWXUQHGE\WKHYLHZ·V
6(/(&7VWDWHPHQWRUHOVHQRYLHZFROXPQQDPHVVKRXOGEHVSHFLILHG
7KHVHOHFWFODXVHLVDVWDQGDUG6(/(&7VWDWHPHQW WKDWVSHFLILHVWKHVHOHFWLRQFULWHULDIRUURZV
WRLQFOXGHLQWKHYLHZ$6(/(&7LQDYLHZFDQQRWLQFOXGHDQ25'(5%<FODXVH,Q'64/LW
FDQQRWLQFOXGHD81,21FODXVH
7KHRSWLRQDO:,7+&+(&.237,21UHVWULFWVLQVHUWVXSGDWHVDQGGHOHWHVLQDYLHZWKDWFDQ
EHXSGDWHG)RUPRUHLQIRUPDWLRQDERXWYLHZVWKDWDOORZXSGDWHDQGDERXWWKH:,7+
&+(&.237,21VHH´&UHDWLQJDYLHZIRUXSGDWHµRQSDJH 

74 INTERBASE 5
CREATING METADATA

7RFUHDWHDUHDGRQO\YLHZDYLHZ·VFUHDWRUPXVWKDYH6(/(&7SULYLOHJHIRUWKHWDEOHRUWDEOHV
XQGHUO\LQJWKHYLHZ7RFUHDWHDYLHZIRUXSGDWHUHTXLUHV$//SULYLOHJH IRUWKHWDEOHRUWDEOHV
XQGHUO\LQJWKHYLHZ)RUPRUHLQIRUPDWLRQDERXW64/SULYLOHJHVVHHWKHVHFXULW\FKDSWHULQ
WKH'DWD'HILQLWLRQ*XLGH

4 &UHDWLQJDYLHZIRU6(/(&7
0DQ\YLHZVFRPELQHGDWDIURPPXOWLSOHWDEOHVRURWKHUYLHZV$YLHZEDVHGRQPXOWLSOH
WDEOHVRURWKHUYLHZVFDQEHUHDGEXWQRWXSGDWHG)RUH[DPSOHWKHIROORZLQJVWDWHPHQW
FUHDWHVDUHDGRQO\YLHZ3+21(B/,67EHFDXVHLWMRLQVWZRWDEOHV(03/2<((DQG
'(3$570(17
EXEC SQL
CREATE VIEW PHONE_LIST AS
SELECT EMP_NO, FIRST_NAME, LAST_NAME, LOCATION, PHONE_NO
FROM EMPLOYEE, DEPARTMENT
WHERE EMPLOYEE.DEPT_NO = DEPARTMENT.DEPT_NO;
EXEC SQL
COMMIT;

,03257$17 2QO\DYLHZ·VFUHDWRULQLWLDOO\KDVDFFHVVWRLW7RDVVLJQUHDGDFFHVVWRRWKHUVXVH*5$17
)RUPRUHLQIRUPDWLRQDERXW*5$17VHHWKHVHFXULW\FKDSWHURIWKH'DWD'HILQLWLRQ*XLGH

4 &UHDWLQJDYLHZIRUXSGDWH
$QXSGDWDEOHYLHZLVRQHWKDWHQDEOHVSULYLOHJHGXVHUVWRLQVHUWXSGDWHDQGGHOHWHLQIRUPDWLRQ
LQWKHYLHZ·VEDVHWDEOH7REHXSGDWDEOHDYLHZPXVWPHHWWKHIROORZLQJFRQGLWLRQV
g ,WGHULYHVLWVFROXPQVIURPDVLQJOHWDEOHRUXSGDWDEOHYLHZ
g ,WGRHVQRWGHILQHDVHOIMRLQRIWKHEDVHWDEOH
g ,WGRHVQRWUHIHUHQFHFROXPQVGHULYHGIURPDULWKPHWLFH[SUHVVLRQV
g 7KHYLHZ·V6(/(&7VWDWHPHQWGRHVQRWFRQWDLQ
à $:+(5(FODXVHWKDWXVHVWKH',67,1&7SUHGLFDWH
à $+$9,1*FODXVH
à )XQFWLRQV
à 1HVWHGTXHULHV
à 6WRUHGSURFHGXUHV
,QWKHIROORZLQJYLHZ+,*+B&,7,(6LVDQXSGDWDEOHYLHZ,WVHOHFWVDOOFLWLHVLQWKH&,7,(6
WDEOHZLWKDOWLWXGHVJUHDWHUWKDQRUHTXDOWRDKDOIPLOH
EXEC SQL
CREATE VIEW HIGH_CITIES AS

PROGRAMMER’S GUIDE 75
CHAPTER 5 WORKING WITH DATA DEFINITION STATEMENTS

SELECT CITY, COUNTRY_NAME, ALTITUDE FROM CITIES


WHERE ALTITUDE >= 2640;
EXEC SQL
COMMIT;

8VHUVZKRKDYH,16(57DQG83'$7(SULYLOHJHVIRUWKLVYLHZFDQFKDQJHURZVLQRUDGGQHZ
URZVWRWKHYLHZ·VXQGHUO\LQJWDEOH&,7,(67KH\FDQHYHQLQVHUWRUXSGDWHURZVWKDWFDQQRW
EHGLVSOD\HGE\WKH+,*+B&,7,(6YLHZ7KHIROORZLQJ,16(57DGGVDUHFRUGIRU6DQWD&UX]
&DOLIRUQLDDOWLWXGHIHHWWRWKH&,7,(6WDEOH
EXEC SQL
INSERT INTO HIGH_CITIES (CITY, COUNTRY_NAME, ALTITUDE)
VALUES ("Santa Cruz", "United States", "23");

7RUHVWULFWLQVHUWVDQGXSGDWHVWKURXJKDYLHZWRRQO\WKRVHURZVWKDWFDQEHVHOHFWHGE\WKH
YLHZXVHWKH:,7+&+(&.237,21LQWKHYLHZGHILQLWLRQ)RUH[DPSOHWKHIROORZLQJ
VWDWHPHQWGHILQHVWKHYLHZ+,*+B&,7,(6WRXVHWKH:,7+&+(&.237,218VHUVZLWK
,16(57DQG83'$7(SULYLOHJHVZLOOEHDEOHWRHQWHUURZVRQO\IRUFLWLHVZLWKDOWLWXGHVJUHDWHU
WKDQRUHTXDOWRDKDOIPLOH
EXEC SQL
CREATE VIEW HIGH_CITIES AS
SELECT CITY, COUNTRY_NAME, ALTITUDE FROM CITIES
WHERE ALTITUDE > 2640 WITH CHECK OPTION;

Creating an index
64/SURYLGHV&5($7(,1'(;IRUHVWDEOLVKLQJXVHUGHILQHGGDWDEDVHLQGH[HV$QLQGH[
EDVHGRQRQHRUPRUHFROXPQVLQDWDEOHLVXVHGWRVSHHGGDWDUHWULHYDOIRUTXHULHVWKDWDFFHVV
WKRVHFROXPQV7KHV\QWD[IRU&5($7(,1'(;LV
EXEC SQL
CREATE [UNIQUE] [ASC[ENDING] | DESC[ENDING]] INDEX <index> ON
table (col [, col ...]);

)RUH[DPSOHWKHIROORZLQJVWDWHPHQWGHILQHVDQLQGH[1$0(;IRUWKH/$67B1$0(DQG
),567B1$0(FROXPQVLQWKH(03/2<((WDEOH
EXEC SQL
CREATE INDEX NAMEX ON EMPLOYEE (LAST_NAME, FIRST_NAME);
Note ,QWHU%DVHDXWRPDWLFDOO\JHQHUDWHVV\VWHPOHYHOLQGH[HVZKHQWDEOHVDUHGHILQHGXVLQJ
81,48(DQG35,0$5<.(<FRQVWUDLQWV)RUPRUHLQIRUPDWLRQDERXWFRQVWUDLQWVVHHWKH
'DWD'HILQLWLRQ*XLGH
6HHWKH/DQJXDJH5HIHUHQFHIRUPRUHLQIRUPDWLRQDERXW&5($7(,1'(;V\QWD[

76 INTERBASE 5
CREATING METADATA

4 3UHYHQWLQJGXSOLFDWHLQGH[HQWULHV
7RGHILQHDQLQGH[WKDWHOLPLQDWHVGXSOLFDWHHQWULHVLQFOXGHWKH81,48(NH\ZRUGLQ&5($7(
,1'(;7KHIROORZLQJVWDWHPHQWFUHDWHVDXQLTXHLQGH[352'7<3(;RQWKH352-(&7WDEOH
EXEC SQL
CREATE UNIQUE INDEX PRODTYPEX ON PROJECT (PRODUCT, PROJ_NAME);

,03257$17 $IWHUDXQLTXHLQGH[LVGHILQHGXVHUVFDQQRWLQVHUWRUXSGDWHYDOXHVLQLQGH[HGFROXPQVLI
WKRVHYDOXHVDOUHDG\H[LVWWKHUH)RUXQLTXHLQGH[HVGHILQHGRQPXOWLSOHFROXPQVOLNH
352'7<3(;LQWKHSUHYLRXVH[DPSOHWKHVDPHYDOXHFDQEHHQWHUHGZLWKLQLQGLYLGXDO
FROXPQVEXWWKHFRPELQDWLRQRIYDOXHVHQWHUHGLQDOOFROXPQVGHILQHGIRUWKHLQGH[PXVW
EHXQLTXH

4 6SHFLI\LQJLQGH[VRUWRUGHU
%\GHIDXOW64/VWRUHVDQLQGH[LQDVFHQGLQJRUGHU7RPDNHDGHVFHQGLQJVRUWRQDFROXPQ
RUJURXSRIFROXPQVPRUHHIILFLHQWXVHWKH'(6&(1',1*NH\ZRUGWRGHILQHWKHLQGH[)RU
H[DPSOHWKHIROORZLQJVWDWHPHQWFUHDWHVDQLQGH[&+$1*(;EDVHGRQWKH&+$1*(B'$7(
FROXPQLQWKH6$/$5<B+,6725<WDEOH
EXEC SQL
CREATE DESCENDING INDEX CHANGEX ON SALARY_HISTORY (CHANGE_DATE);
Note 7RUHWULHYHLQGH[HGGDWDLQGHVFHQGLQJRUGHUXVH25'(5%<LQWKH6(/(&7VWDWHPHQW
WRVSHFLI\UHWULHYDORUGHU

Creating generators
$JHQHUDWRULVDPRQRWRQLFDOO\LQFUHDVLQJRUGHFUHDVLQJQXPHULFYDOXHWKDWLVLQVHUWHGLQDILHOG
HLWKHUGLUHFWO\E\DQ64/VWDWHPHQWLQDQDSSOLFDWLRQRUWKURXJKDWULJJHU*HQHUDWRUVDUH
RIWHQXVHGWRSURGXFHXQLTXHYDOXHVWRLQVHUWLQWRDFROXPQXVHGDVDSULPDU\NH\
7RFUHDWHDJHQHUDWRUIRUXVHLQDQDSSOLFDWLRQXVHWKHIROORZLQJ&5($7(*(1(5$725
V\QWD[
EXEC SQL
CREATE GENERATOR name;

7KHIROORZLQJVWDWHPHQWFUHDWHVDJHQHUDWRU(03B12B*(1WRVSHFLI\DXQLTXHHPSOR\HH
QXPEHU
EXEC SQL
CREATE GENERATOR EMP_NO_GEN;
EXEC SQL
COMMIT;

PROGRAMMER’S GUIDE 77
CHAPTER 5 WORKING WITH DATA DEFINITION STATEMENTS

2QFHDJHQHUDWRULVFUHDWHGWKHVWDUWLQJYDOXHIRUDJHQHUDWHGQXPEHUFDQEHVSHFLILHGZLWK
6(7*(1(5$7257RLQVHUWDJHQHUDWHGQXPEHULQDILHOGXVHWKH,QWHU%DVHOLEUDU\
*(1B,' IXQFWLRQLQDQDVVLJQPHQWVWDWHPHQW)RUPRUHLQIRUPDWLRQDERXW*(1B,' 
&5($7(*(1(5$725DQG6(7*(1(5$725VHHWKH'DWD'HILQLWLRQ*XLGH

Dropping metadata
64/VXSSRUWVVHYHUDOVWDWHPHQWVIRUGHOHWLQJH[LVWLQJPHWDGDWD
g '5237$%/(WRGHOHWHDWDEOHIURPDGDWDEDVH
g '5239,(:WRGHOHWHDYLHZGHILQLWLRQIURPDGDWDEDVH
g '523,1'(;WRGHOHWHDGDWDEDVHLQGH[
g $/7(57$%/(WRGHOHWHFROXPQVIURPDWDEOH
)RUPRUHLQIRUPDWLRQDERXWGHOHWLQJFROXPQVZLWK$/7(57$%/(VHH´$OWHULQJDWDEOHµRQ
SDJH 

Dropping an index
7RGHOHWHDQLQGH[XVH'523,1'(;$QLQGH[FDQRQO\EHGURSSHGE\LWVFUHDWRUWKH
6<6'%$RUDXVHUZLWKURRWSULYLOHJHV,IDQLQGH[LVLQXVHZKHQWKHGURSLVDWWHPSWHGWKH
GURSLVSRVWSRQHGXQWLOWKHLQGH[LVQRORQJHULQXVH7KHV\QWD[RI'523,1'(;LV
EXEC SQL
DROP INDEX name;

QDPHLVWKHQDPHRIWKHLQGH[WRGHOHWH)RUH[DPSOHWKHIROORZLQJVWDWHPHQWGURSVWKHLQGH[
1((';
EXEC SQL
DROP INDEX NEEDX;
EXEC SQL
COMMIT;
'HOHWLRQIDLOVLIWKHLQGH[LVRQD81,48(35,0$5<.(<RU)25(,*1.(<LQWHJULW\
FRQVWUDLQW7RGURSDQLQGH[RQD81,48(35,0$5<.(<RU)25(,*1.(<LQWHJULW\
FRQVWUDLQWILUVWGURSWKHFRQVWUDLQWVWKHFRQVWUDLQHGFROXPQVRUWKHWDEOH
)RUPRUHLQIRUPDWLRQDERXW'523,1'(;DQGGURSSLQJLQWHJULW\FRQVWUDLQWVVHHWKH'DWD
'HILQLWLRQ*XLGH

78 INTERBASE 5
DROPPING METADATA

Dropping a view
7RGHOHWHDYLHZXVH'5239,(:$YLHZFDQRQO\EHGURSSHGE\LWVRZQHUWKH6<6'%$RU
DXVHUZLWKURRWSULYLOHJHV,IDYLHZLVLQXVHZKHQDGURSLVDWWHPSWHGWKHGURSLVSRVWSRQHG
XQWLOWKHYLHZLVQRORQJHULQXVH7KHV\QWD[RI'5239,(:LV
EXEC SQL
DROP VIEW name;

7KHIROORZLQJVWDWHPHQWGURSVWKH(03/2<((B6$/$5<YLHZ
EXEC SQL
DROP VIEW EMPLOYEE_SALARY;
EXEC SQL
COMMIT;

'HOHWLQJDYLHZIDLOVLIDYLHZLVXVHGLQDQRWKHUYLHZDWULJJHURUDFRPSXWHGFROXPQ7R
GHOHWHDYLHZWKDWPHHWVDQ\RIWKHVHFRQGLWLRQV
 'HOHWHWKHRWKHUYLHZWULJJHURUFRPSXWHGFROXPQ
 'HOHWHWKHYLHZ
)RUPRUHLQIRUPDWLRQDERXW'5239,(:VHHWKH'DWD'HILQLWLRQ*XLGH

Dropping a table
8VH'5237$%/(WRUHPRYHDWDEOHIURPDGDWDEDVH$WDEOHFDQRQO\EHGURSSHGE\LWV
RZQHUWKH6<6'%$RUDXVHUZLWKURRWSULYLOHJHV,IDWDEOHLVLQXVHZKHQDGURSLVDWWHPSWHG
WKHGURSLVSRVWSRQHGXQWLOWKHWDEOHLVQRORQJHULQXVH7KHV\QWD[RI'5237$%/(LV
EXEC SQL
DROP TABLE name;

QDPHLVWKHQDPHRIWKHWDEOHWRGURS)RUH[DPSOHWKHIROORZLQJVWDWHPHQWGURSVWKH
(03/2<((WDEOH
EXEC SQL
DROP TABLE EMPLOYEE;
EXEC SQL
COMMIT;

'HOHWLQJDWDEOHIDLOVLIDWDEOHLVXVHGLQDYLHZDWULJJHURUDFRPSXWHGFROXPQ$WDEOH
FDQQRWEHGHOHWHGLID81,48(RU35,0$5<.(<LQWHJULW\FRQVWUDLQWLVGHILQHGIRULWDQGWKH
FRQVWUDLQWLVDOVRUHIHUHQFHGE\D)25(,*1.(<LQDQRWKHUWDEOH7RGURSWKHWDEOHILUVWGURS
WKH)25(,*1.(<FRQVWUDLQWVLQWKHRWKHUWDEOHWKHQGURSWKHWDEOH

PROGRAMMER’S GUIDE 79
CHAPTER 5 WORKING WITH DATA DEFINITION STATEMENTS

Note &ROXPQVZLWKLQDWDEOHFDQEHGURSSHGZLWKRXWGURSSLQJWKHUHVWRIWKHWDEOH)RU
PRUHLQIRUPDWLRQVHH´'URSSLQJDQH[LVWLQJFROXPQµRQSDJH 
)RUPRUHLQIRUPDWLRQDERXW'5237$%/(VHHWKH'DWD'HILQLWLRQ*XLGH

Altering metadata
0RVWFKDQJHVWRGDWDGHILQLWLRQVDUHPDGHDWWKHWDEOHOHYHODQGLQYROYHDGGLQJQHZFROXPQV
WRDWDEOHRUGURSSLQJREVROHWHFROXPQVIURPLW64/SURYLGHV$/7(57$%/(WRDGGQHZ
FROXPQVWRDWDEOHDQGWRGURSH[LVWLQJFROXPQV$VLQJOH$/7(57$%/(FDQFDUU\RXWDVLQJOH
RSHUDWLRQRUERWKRSHUDWLRQV
0DNLQJFKDQJHVWRYLHZVDQGLQGH[HVDOZD\VUHTXLUHVWZRVHSDUDWHVWDWHPHQWV
 'URSWKHH[LVWLQJGHILQLWLRQ
 &UHDWHDQHZGHILQLWLRQ
,IFXUUHQWPHWDGDWDFDQQRWEHGURSSHGUHSODFHPHQWGHILQLWLRQVFDQQRWEHDGGHG'URSSLQJ
PHWDGDWDFDQIDLOIRUWKHIROORZLQJUHDVRQV
g 7KHSHUVRQDWWHPSWLQJWRGURSPHWDGDWDLVQRWWKHPHWDGDWD·VFUHDWRU
g 64/LQWHJULW\FRQVWUDLQWVDUHGHILQHGIRUWKHPHWDGDWDDQGUHIHUHQFHGLQRWKHUPHWDGDWD
g 7KHPHWDGDWDLVXVHGLQDQRWKHUYLHZWULJJHURUFRPSXWHGFROXPQ
)RUPRUHLQIRUPDWLRQDERXWGURSSLQJPHWDGDWDVHH´'URSSLQJPHWDGDWDµRQSDJH 

Altering a table
$/7(57$%/(HQDEOHVWKHIROORZLQJFKDQJHVWRDQH[LVWLQJWDEOH
g $GGLQJQHZFROXPQGHILQLWLRQV
g $GGLQJQHZWDEOHFRQVWUDLQWV
g 'URSSLQJH[LVWLQJFROXPQGHILQLWLRQV
g 'URSSLQJH[LVWLQJWDEOHFRQVWUDLQWV
g &KDQJLQJFROXPQGHILQLWLRQVE\GURSSLQJH[LVWLQJGHILQLWLRQVDQGDGGLQJQHZRQHV
g &KDQJLQJH[LVWLQJWDEOHFRQVWUDLQWVE\GURSSLQJH[LVWLQJGHILQLWLRQVDQGDGGLQJQHZRQHV
7KHVLPSOHV\QWD[RI$/7(57$%/(LVDVIROORZV
EXEC SQL

80 INTERBASE 5
ALTERING METADATA

ALTER TABLE name {ADD colname <datatype> [NOT NULL]


| DROP colname | ADD CONSTRAINT constraintname tableconstraint
| DROP CONSTRAINT constraintname};
Note )RULQIRUPDWLRQDERXWDGGLQJGURSSLQJDQGPRGLI\LQJFRQVWUDLQWVDWWKHWDEOHOHYHO
VHHWKH'DWD'HILQLWLRQ*XLGH
)RUWKHFRPSOHWHV\QWD[RI$/7(57$%/(VHHWKH/DQJXDJH5HIHUHQFH

4 $GGLQJDQHZFROXPQWRDWDEOH
7RDGGDQRWKHUFROXPQWRDQH[LVWLQJWDEOHXVH$/7(57$%/($WDEOHFDQRQO\EHPRGLILHG
E\LWVFUHDWRU7KHV\QWD[IRUDGGLQJDFROXPQZLWK$/7(57$%/(LV
EXEC SQL
ALTER TABLE name ADD colname <datatype> colconstraint
[, ADD colname datatype colconstraint ...];

)RUH[DPSOHWKHIROORZLQJVWDWHPHQWDGGVDFROXPQ(03B12WRWKH(03/2<((WDEOH
EXEC SQL
ALTER TABLE EMPLOYEE ADD EMP_NO EMPNO NOT NULL;
EXEC SQL
COMMIT;

7KLVH[DPSOHPDNHVXVHRIDGRPDLQ(0312WRGHILQHDFROXPQ)RUPRUHLQIRUPDWLRQ
DERXWGRPDLQVVHHWKH'DWD'HILQLWLRQ*XLGH
0XOWLSOHFROXPQVFDQEHDGGHGWRDWDEOHDWWKHVDPHWLPH6HSDUDWHFROXPQGHILQLWLRQVZLWK
FRPPDV)RUH[DPSOHWKHIROORZLQJVWDWHPHQWDGGVWZRFROXPQV(03B12DQG
)8//B1$0(WRWKH(03/2<((WDEOH)8//B1$0(LVDFRPSXWHGFROXPQDFROXPQWKDW
GHULYHVLWYDOXHVIURPFDOFXODWLRQVEDVHGRQRWKHUFROXPQV
EXEC SQL
ALTER TABLE EMPLOYEE
ADD EMP_NO EMPNO NOT NULL,
ADD FULL_NAME COMPUTED BY (LAST_NAME || ’, ’ || FIRST_NAME);
EXEC SQL
COMMIT;

7KLVH[DPSOHFUHDWHVDFROXPQXVLQJDYDOXHFRPSXWHGIURPWZRRWKHUFROXPQVDOUHDG\
GHILQHGIRUWKH(03/2<((WDEOH)RUPRUHLQIRUPDWLRQDERXWFUHDWLQJFRPSXWHGFROXPQV
VHHWKH'DWD'HILQLWLRQ*XLGH
1HZFROXPQVDGGHGWRDWDEOHFDQEHGHILQHGZLWKLQWHJULW\FRQVWUDLQWV)RUPRUH
LQIRUPDWLRQDERXWDGGLQJFROXPQVZLWKLQWHJULW\FRQVWUDLQWVWRDWDEOHVHHWKH'DWD'HILQLWLRQ
*XLGH

PROGRAMMER’S GUIDE 81
CHAPTER 5 WORKING WITH DATA DEFINITION STATEMENTS

4 'URSSLQJDQH[LVWLQJFROXPQ
7RGHOHWHDFROXPQGHILQLWLRQDQGLWVGDWDIURPDWDEOHXVH$/7(57$%/($FROXPQFDQRQO\
EHGURSSHGE\WKHRZQHURIWKHWDEOHWKH6<6'%$RUDXVHUZLWKURRWSULYLOHJHV,IDWDEOHLV
LQXVHZKHQDFROXPQLVGURSSHGWKHGURSLVSRVWSRQHGXQWLOWKHWDEOHLVQRORQJHULQXVH
7KHV\QWD[IRUGURSSLQJDFROXPQZLWK$/7(57$%/(LV
EXEC SQL
ALTER TABLE name DROP colname [, colname ...];

)RUH[DPSOHWKHIROORZLQJVWDWHPHQWGURSVWKH(03B12FROXPQIURPWKH(03/2<((WDEOH
EXEC SQL
ALTER TABLE EMPLOYEE DROP EMP_NO;
EXEC SQL
COMMIT;

0XOWLSOHFROXPQVFDQEHGURSSHGZLWKDVLQJOH$/7(57$%/(7KHIROORZLQJVWDWHPHQW
GURSVWKH(03B12DQG)8//B1$0(FROXPQVIURPWKH(03/2<((WDEOH
EXEC SQL
ALTER TABLE EMPLOYEE
DROP EMP_NO,
DROP FULL_NAME;
EXEC SQL
COMMIT;

'HOHWLQJDFROXPQIDLOVLIWKHFROXPQLVSDUWRID81,48(35,0$5<.(<RU)25(,*1.(<
FRQVWUDLQW7RGURSWKHFROXPQILUVWGURSWKHFRQVWUDLQWWKHQWKHFROXPQ
'HOHWLQJDFROXPQDOVRIDLOVLIWKHFROXPQLVXVHGE\D&+(&.FRQVWUDLQWIRUDQRWKHUFROXPQ
7RGURSWKHFROXPQILUVWGURSWKH&+(&.FRQVWUDLQWWKHQGURSWKHFROXPQ
)RUPRUHLQIRUPDWLRQDERXWLQWHJULW\FRQVWUDLQWVVHHWKH'DWD'HILQLWLRQ*XLGH

4 0RGLI\LQJDFROXPQ
$QH[LVWLQJFROXPQGHILQLWLRQFDQEHPRGLILHGXVLQJ$/7(57$%/(EXWLIGDWDDOUHDG\VWRUHG
LQWKDWFROXPQLVQRWSUHVHUYHGEHIRUHPDNLQJFKDQJHVLWZLOOEHORVW
3UHVHUYLQJGDWDHQWHUHGLQDFROXPQDQGPRGLI\LQJWKHGHILQLWLRQIRUDFROXPQLVDVL[VWHS
SURFHVV
 $GGLQJDQHZWHPSRUDU\FROXPQWRWKHWDEOHWKDWPLUURUVWKHFXUUHQWPHWDGDWD
RIWKHFROXPQWREHFKDQJHG
 &RS\LQJWKHGDWDIURPWKHFROXPQWREHFKDQJHGWRWKHQHZO\FUHDWHGWHPSRUDU\
FROXPQ
 'URSSLQJWKHFROXPQWRFKDQJH

82 INTERBASE 5
ALTERING METADATA

 $GGLQJDQHZFROXPQGHILQLWLRQJLYLQJLWWKHVDPHQDPHWKDWWKHSUHYLRXVO\
GURSSHGFROXPQKDG
 &RS\LQJGDWDIURPWKHWHPSRUDU\FROXPQWRWKHUHGHILQHGFROXPQ
 'URSSLQJWKHWHPSRUDU\FROXPQ
)RUH[DPSOHVXSSRVHWKH(03/2<((WDEOHFRQWDLQVDFROXPQ2)),&(B12GHILQHGWRKROG
DGDWDW\SHRI&+$5  DQGVXSSRVHWKDWWKHVL]HRIWKHFROXPQQHHGVWREHLQFUHDVHGE\RQH
7KHIROORZLQJQXPEHUHGVHTXHQFHGHVFULEHVHDFKVWHSDQGSURYLGHVVDPSOHFRGH
 )LUVWFUHDWHDWHPSRUDU\FROXPQWRKROGWKHGDWDLQ2)),&(B12GXULQJWKH
PRGLILFDWLRQSURFHVV
EXEC SQL
ALTER TABLE EMPLOYEE ADD TEMP_NO CHAR(3);
EXEC SQL
COMMIT;
 0RYHH[LVWLQJGDWDIURP2)),&(B12WR7(03B12WRSUHVHUYHLW
EXEC SQL
UPDATE EMPLOYEE
SET TEMP_NO = OFFICE_NO;
 $IWHUWKHGDWDLVPRYHGGURSWKH2)),&(B12FROXPQ
EXEC SQL
ALTER TABLE DROP OFFICE_NO;
EXEC SQL
COMMIT;
 $GGDQHZFROXPQGHILQLWLRQIRU2)),&(B12VSHFLI\LQJWKHGDWDW\SHDQG
QHZVL]H
EXEC SQL
ALTER TABLE ADD OFFICE_NO CHAR (4);
EXEC SQL
COMMIT;
 0RYHWKHGDWDIURP7(03B12WR2)),&(B12
EXEC SQL
UPDATE EMPLOYEE
SET OFFICE_NO = TEMP_NO;
 )LQDOO\GURSWKH7(03B12FROXPQ
EXEC SQL
ALTER TABLE DROP TEMP_NO;
EXEC SQL
COMMIT;

PROGRAMMER’S GUIDE 83
CHAPTER 5 WORKING WITH DATA DEFINITION STATEMENTS

)RUPRUHLQIRUPDWLRQDERXWGURSSLQJFROXPQGHILQLWLRQVVHH´'URSSLQJDQH[LVWLQJ
FROXPQµRQSDJH )RUPRUHLQIRUPDWLRQDERXWDGGLQJFROXPQGHILQLWLRQVVHH´$GGLQJD
QHZFROXPQWRDWDEOHµRQSDJH 

Altering a view
7RFKDQJHWKHLQIRUPDWLRQSURYLGHGE\DYLHZIROORZWKHVHVWHSV
 'URSWKHFXUUHQWYLHZGHILQLWLRQ
 &UHDWHDQHZYLHZGHILQLWLRQDQGJLYHLWWKHVDPHQDPHDVWKHGURSSHGYLHZ
)RUH[DPSOHWKHIROORZLQJYLHZLVGHILQHGWRVHOHFWHPSOR\HHVDODU\LQIRUPDWLRQ
EXEC SQL
CREATE VIEW EMPLOYEE_SALARY AS
SELECT EMP_NO, LAST_NAME, CURRENCY, SALARY
FROM EMPLOYEE, COUNTRY
WHERE EMPLOYEE.COUNTRY_CODE = COUNTRY.CODE;

6XSSRVHWKHIXOOQDPHRIHDFKHPSOR\HHVKRXOGEHGLVSOD\HGLQVWHDGRIWKHODVWQDPH)LUVW
GURSWKHFXUUHQWYLHZGHILQLWLRQ
EXEC SQL
DROP EMPLOYEE_SALARY;
EXEC SQL
COMMIT;

7KHQFUHDWHDQHZYLHZGHILQLWLRQWKDWGLVSOD\VHDFKHPSOR\HH·VIXOOQDPH
EXEC SQL
CREATE VIEW EMPLOYEE_SALARY AS
SELECT EMP_NO, FULL_NAME, CURRENCY, SALARY
FROM EMPLOYEE, COUNTRY
WHERE EMPLOYEE.COUNTRY_CODE = COUNTRY.CODE;
EXEC SQL
COMMIT;

Altering an index
7RFKDQJHWKHGHILQLWLRQRIDQLQGH[IROORZWKHVHVWHSV
 8VH$/7(5,1'(;WRPDNHWKHFXUUHQWLQGH[LQDFWLYH
 'URSWKHFXUUHQWLQGH[

84 INTERBASE 5
ALTERING METADATA

 &UHDWHDQHZLQGH[DQGJLYHLWWKHVDPHQDPHDVWKHGURSSHGLQGH[
$QLQGH[LVXVXDOO\PRGLILHGWRFKDQJHWKHFRPELQDWLRQRIFROXPQVWKDWDUHLQGH[HGWR
SUHYHQWRUDOORZLQVHUWLRQRIGXSOLFDWHHQWULHVRUWRVSHFLI\LQGH[VRUWRUGHU)RUH[DPSOH
JLYHQWKHIROORZLQJGHILQLWLRQRIWKH1$0(;LQGH[
EXEC SQL
CREATE INDEX NAMEX ON EMPLOYEE (LAST_NAME, FIRST_NAME);

6XSSRVHWKHUHLVDQDGGLWLRQDOQHHGWRSUHYHQWGXSOLFDWHHQWULHVZLWKWKH81,48(NH\ZRUG
)LUVWPDNHWKHFXUUHQWLQGH[LQDFWLYHWKHQGURSLW
EXEC SQL
ALTER INDEX NAMEX INACTIVE;
EXEC SQL
DROP INDEX NAMEX;
EXEC SQL
COMMIT;
7KHQFUHDWHDQHZLQGH[1$0(;EDVHGRQWKHSUHYLRXVGHILQLWLRQWKDWDOVRLQFOXGHVWKH
81,48(NH\ZRUG
EXEC SQL
CREATE UNIQUE INDEX NAMEX ON EMPLOYEE (LAST_NAME, FIRST_NAME);
EXEC SQL
COMMIT

$/7(5,1'(;FDQEHXVHGGLUHFWO\WRFKDQJHDQLQGH[·VVRUWRUGHURUWRDGGWKHDELOLW\WR
KDQGOHXQLTXHRUGXSOLFDWHHQWULHV)RUH[DPSOHWKHIROORZLQJVWDWHPHQWFKDQJHVWKH1$0(;
LQGH[WRSHUPLWGXSOLFDWHHQWULHV
EXEC SQL
ALTER INDEX NAMEX DUPLICATE;

,03257$17 %HFDUHIXOZKHQDOWHULQJDQLQGH[GLUHFWO\)RUH[DPSOHFKDQJLQJDQLQGH[IURPVXSSRUWLQJ
GXSOLFDWHHQWULHVWRRQHWKDWUHTXLUHVXQLTXHHQWULHVZLWKRXWGLVDEOLQJWKHLQGH[DQG
UHFUHDWLQJLWFDQUHGXFHLQGH[SHUIRUPDQFH
)RUPRUHLQIRUPDWLRQDERXWGURSSLQJDQLQGH[VHH´'URSSLQJDQLQGH[µRQSDJH )RU
PRUHLQIRUPDWLRQDERXWFUHDWLQJDQLQGH[VHH´&UHDWLQJDQLQGH[µRQSDJH 

PROGRAMMER’S GUIDE 85
CHAPTER

Working with Data


Chapter6
6
7KHPDMRULW\RI64/VWDWHPHQWVLQDQHPEHGGHGSURJUDPDUHGHYRWHGWRUHDGLQJRU
PRGLI\LQJH[LVWLQJGDWDRUDGGLQJQHZGDWDWRDGDWDEDVH7KLVFKDSWHUGHVFULEHVWKHW\SHV
RIGDWDUHFRJQL]HGE\,QWHU%DVHDQGKRZWRUHWULHYHPRGLI\DGGRUGHOHWHGDWDLQDGDWDEDVH
XVLQJ64/H[SUHVVLRQVDQGWKHIROORZLQJVWDWHPHQWV
g 6(/(&7VWDWHPHQWVTXHU\DGDWDEDVHWKDWLVUHDGRUUHWULHYHH[LVWLQJGDWDIURPDGDWDEDVH
9DULDWLRQVRIWKH6(/(&7VWDWHPHQWPDNHLWSRVVLEOHWRUHWULHYH
à $VLQJOHURZRUSDUWRIDURZIURPDWDEOH7KLVRSHUDWLRQLVUHIHUUHGWRDVDVLQJOHWRQVHOHFW
à 0XOWLSOHURZVRUSDUWVRIURZVIURPDWDEOHXVLQJD6(/(&7ZLWKLQD'(&/$5(&85625
VWDWHPHQW
à 5HODWHGURZVRUSDUWVRIURZVIURPWZRRUPRUHWDEOHVLQWRDYLUWXDOWDEOHRUUHVXOWVWDEOH
7KLVRSHUDWLRQLVUHIHUUHGWRDVDMRLQ
à $OOURZVRUSDUWVRIURZVIURPWZRRUPRUHWDEOHVLQWRDYLUWXDOWDEOH7KLVRSHUDWLRQLV
UHIHUUHGWRDVDXQLRQ
g ,16(57VWDWHPHQWVZULWHQHZURZVRIGDWDWRDWDEOH
g 83'$7(VWDWHPHQWVPRGLI\H[LVWLQJURZVRIGDWDLQDWDEOH
g '(/(7(VWDWHPHQWVUHPRYHH[LVWLQJURZVRIGDWDIURPDWDEOH

87
CHAPTER 6 WORKING WITH DATA

7ROHDUQKRZWRXVHWKH6(/(&7VWDWHPHQWWRUHWULHYHGDWDVHH´8QGHUVWDQGLQJGDWDUHWULHYDO
ZLWK6(/(&7µRQSDJH )RULQIRUPDWLRQDERXWUHWULHYLQJDVLQJOHURZZLWK6(/(&7VHH
´6HOHFWLQJDVLQJOHURZµRQSDJH )RULQIRUPDWLRQDERXWUHWULHYLQJPXOWLSOHURZVVHH
´6HOHFWLQJPXOWLSOHURZVµRQSDJH 
)RULQIRUPDWLRQDERXWXVLQJ,16(57WRZULWHQHZGDWDWRDWDEOHVHH´,QVHUWLQJGDWDµRQ
SDJH 7RPRGLI\GDWDZLWK83'$7(VHH´8SGDWLQJGDWDµRQSDJH 7RUHPRYHGDWD
IURPDWDEOHZLWK'(/(7(VHH´'HOHWLQJGDWDµRQSDJH 

Supported datatypes
7RTXHU\RUZULWHWRDWDEOHLWLVQHFHVVDU\WRNQRZWKHVWUXFWXUHRIWKHWDEOHZKDWFROXPQV
LWFRQWDLQVDQGZKDWGDWDW\SHVDUHGHILQHGIRUWKRVHFROXPQV,QWHU%DVHVXSSRUWVWHQ
IXQGDPHQWDOGDWDW\SHVGHVFULEHGLQWKHIROORZLQJWDEOH

Name Size Range/Precision Description


Blob Variable None. Blob segment size is limited to 64K. Binary large object. Stores large data,
such as graphics, text, and digitized voice.
Basic structural unit: segment. Blob
subtype describes Blob contents.
CHAR(n) n characters 1 to 32,767 bytes. Fixed length CHAR or text string type.
Character set character size determines Alternate keyword: CHARACTER.
the maximum number of characters that
can fit in 32K.
DATE 64 bits 1 Jan 100 to 11 Dec 5941. Also includes time information.
DECIMAL (precision, Variable precision = 1 to 15. Specifies at least Number with a decimal point scale digits
scale) precision digits of precision to store. from the right. For example, DECIMAL(10,
scale = 1 to 15. Specifies number of 3) holds numbers accurately in the
following format:
decimal places for storage. Must be less
than or equal to precision. ppppppp.sss
DOUBLE PRECISION 64 bitsa 1.7 x 10–308 to 1.7 x 10308. Scientific: 15 digits of precision.
FLOAT 32 bits 3.4 x 10–38 to 3.4 x 1038. Single precision: 7 digits of precision.
INTEGER 32 bits –2,147,483,648 to 2,147,483,647. Signed long (longword).
TABLE 6.1 Datatypes supported by InterBase

88 INTERBASE 5
SUPPORTED DATATYPES

Name Size Range/Precision Description


NUMERIC (precision, Variable precision = 1 to 15. Specifies exactly Number with a decimal point scale digits
scale) precision digits of precision to store. from the right. For example,
NUMERIC(10,3) holds numbers accurately
scale = 1 to 15. Specifies number of
in the following format:
decimal places for storage. Must be less
than or equal to precision. ppppppp.sss
SMALLINT 16 bits –32,768 to 32,767. Signed short (word).
VARCHAR (n) n characters 1 to 32,765 bytes. Variable length CHAR or text string type.
Character set character size determines Alternate keywords: CHAR VARYING,
the maximum number of characters that CHARACTER VARYING.
can fit in 32K.
TABLE 6.1 Datatypes supported by InterBase (continued)

D $FWXDOVL]HRI'28%/(LVSODWIRUPGHSHQGHQW0RVWSODWIRUPVVXSSRUWWKHELWVL]H

$%ORELVXVHGWRVWRUHODUJHGDWDREMHFWVRILQGHWHUPLQDWHDQGYDULDEOHVL]HVXFKDV
ELWPDSSHGJUDSKLFVLPDJHVYHFWRUGUDZLQJVVRXQGILOHVFKDSWHURUERRNOHQJWKGRFXPHQWV
RUDQ\RWKHUNLQGRIPXOWLPHGLDLQIRUPDWLRQ%HFDXVHD%OREFDQKROGGLIIHUHQWNLQGVRI
LQIRUPDWLRQLWUHTXLUHVVSHFLDOSURFHVVLQJIRUUHDGLQJDQGZULWLQJ)RUPRUHLQIRUPDWLRQ
DERXW%OREKDQGOLQJVHH&KDSWHU´:RUNLQJZLWK%ORE'DWDµ
7KH'$7(GDWDW\SHPD\UHTXLUHFRQYHUVLRQWRDQGIURP,QWHU%DVHZKHQHQWHUHGRU
PDQLSXODWHGLQDKRVWODQJXDJHSURJUDP)RUPRUHLQIRUPDWLRQDERXWUHWULHYLQJDQGZULWLQJ
GDWHVVHH&KDSWHU´:RUNLQJZLWK'DWHVµ
,QWHU%DVHDOVRVXSSRUWVDUUD\VRIPRVWGDWDW\SHV$QDUUD\LVDPDWUL[RILQGLYLGXDOLWHPVDOO
RIDQ\VLQJOH,QWHU%DVHGDWDW\SHH[FHSW%OREWKDWFDQEHKDQGOHGHLWKHUDVDVLQJOHHQWLW\RU
PDQLSXODWHGLWHPE\LWHP7ROHDUQPRUHDERXWWKHIOH[LEOHGDWDDFFHVVSURYLGHGE\DUUD\V
VHH&KDSWHU´8VLQJ$UUD\Vµ
)RUDFRPSOHWHGLVFXVVLRQRI,QWHU%DVHGDWDW\SHVVHHWKH'DWD'HILQLWLRQ*XLGH

PROGRAMMER’S GUIDE 89
CHAPTER 6 WORKING WITH DATA

Understanding SQL expressions


$OO64/GDWDPDQLSXODWLRQVWDWHPHQWVVXSSRUW64/H[SUHVVLRQV64/V\QWD[IRUFRPSDULQJ
DQGHYDOXDWLQJFROXPQVFRQVWDQWVDQGKRVWODQJXDJHYDULDEOHVWRSURGXFHDVLQJOHYDOXH
,QWKH6(/(&7VWDWHPHQWIRUH[DPSOHWKH:+(5(FODXVHLVXVHGWRVSHFLI\DVHDUFKFRQGLWLRQ
WKDWGHWHUPLQHVLIDURZTXDOLILHVIRUUHWULHYDO7KDWVHDUFKFRQGLWLRQLVDQ64/H[SUHVVLRQ
'(/(7(DQG83'$7(DOVRVXSSRUWVHDUFKFRQGLWLRQH[SUHVVLRQV7\SLFDOO\ZKHQDQ
H[SUHVVLRQLVXVHGDVDVHDUFKFRQGLWLRQWKHH[SUHVVLRQHYDOXDWHVWRD%RROHDQYDOXHWKDWLV
7UXH)DOVHRU8QNQRZQ
64/H[SUHVVLRQVFDQDOVRDSSHDULQWKH,16(57VWDWHPHQW9$/8(FODXVHDQGWKH83'$7(
VWDWHPHQW6(7FODXVHWRVSHFLI\RUFDOFXODWHYDOXHVWRLQVHUWLQWRDFROXPQ:KHQLQVHUWLQJRU
XSGDWLQJDQXPHULFYDOXHYLDDQH[SUHVVLRQWKHH[SUHVVLRQLVXVXDOO\DULWKPHWLFVXFKDV
PXOWLSO\LQJRQHQXPEHUE\DQRWKHUWRSURGXFHDQHZQXPEHUZKLFKLVWKHQLQVHUWHGRU
XSGDWHGLQDFROXPQ:KHQLQVHUWLQJRUXSGDWLQJDVWULQJYDOXHWKHH[SUHVVLRQPD\
FRQFDWHQDWHRUFRPELQHWZRVWULQJVWRSURGXFHDVLQJOHVWULQJIRULQVHUWLRQRUXSGDWLQJ
7KHIROORZLQJWDEOHGHVFULEHVWKHHOHPHQWVWKDWFDQEHXVHGLQH[SUHVVLRQV

Element Description
Column names Columns from specified tables, against which to search or compare values, or
from which to calculate values.
Host-language variables Program variables containing changeable values. Host-language variables
must be preceded by a colon (:).
Constants Hard-coded numbers or quoted strings, like 507 or “Tokyo”.
Concatenation operator ||, used to combine character strings.
Arithmetic operators +, –, *, and /, used to calculate and evaluate values.
Logical operators Keywords, NOT, AND, and OR, used within simple search conditions, or to
combine simple search conditions to make complex searches. A logical
operation evaluates to true or false. Usually used only in search conditions.
TABLE 6.2 Elements of SQL expressions

90 INTERBASE 5
UNDERSTANDING SQL EXPRESSIONS

Element Description
Comparison operators <, >, <=, >=, =, and <>, used to compare a value on the left side of the
operator to another on the right. A comparative operation evaluates to true or
false.
Other, more specialized comparison operators include ALL, ANY, BETWEEN,
CONTAINING, EXISTS, IN, IS, LIKE, NULL, SINGULAR, SOME, and STARTING WITH. These
operators can evaluate to True, False, or Unknown. They are usually used only
in search conditions.
COLLATE clause Comparisons of CHAR and VARCHAR values can sometimes take advantage of a
COLLATE clause to force the way text values are compared.

Stored procedures Reusable SQL statement blocks that can receive and return parameters, and
that are stored as part of a database’s metadata.
Subqueries SELECT statements, typically nested in WHERE clauses, that return values to be
compared with the result set of the main SELECT statement.
Parentheses Used to group expressions into hierarchies; operations inside parentheses are
performed before operations outside them. When parentheses are nested,
the contents of the innermost set is evaluated first and evaluation proceeds
outward.
Date literals String values that can be entered in quotes and be interpreted as date values
in SELECT, INSERT, and UPDATE operations. Possible strings are ‘TODAY’, ‘NOW’,
‘YESTERDAY’, and ‘TOMORROW’.
The USER pseudocolumn References the name of the user who is currently logged in. For example, USER
can be used as a default in a column definition or to enter the current user’s
name in an INSERT. When a user name is present in a table, it can be referenced
with USER in SELECT and DELETE statements.
TABLE 6.2 Elements of SQL expressions (continued)

&RPSOH[H[SUHVVLRQVFDQEHFRQVWUXFWHGE\FRPELQLQJVLPSOHH[SUHVVLRQVLQGLIIHUHQWZD\V
)RUH[DPSOHWKHIROORZLQJ:+(5(FODXVHXVHVDFROXPQQDPHWKUHHFRQVWDQWVWKUHH
FRPSDULVRQRSHUDWRUVDQGDVHWRIJURXSLQJSDUHQWKHVHVWRUHWULHYHRQO\WKRVHURZVIRU
HPSOR\HHVZLWKVDODULHVEHWZHHQDQG
WHERE DEPARTMENT = "Publications" AND
(SALARY > 60000 AND SALARY < 120000)

$VDQRWKHUH[DPSOHVHDUFKFRQGLWLRQVLQ:+(5(FODXVHVRIWHQFRQWDLQQHVWHG6(/(&7
VWDWHPHQWVRUVXETXHULHV,QWKHIROORZLQJTXHU\WKH:+(5(FODXVHFRQWDLQVDVXETXHU\WKDW
XVHVWKHDJJUHJDWHIXQFWLRQ$9* WRUHWULHYHDOLVWRIDOOGHSDUWPHQWVZLWKELJJHUWKDQ
DYHUDJHVDODULHV

PROGRAMMER’S GUIDE 91
CHAPTER 6 WORKING WITH DATA

EXEC SQL
DECLARE WELL_PAID CURSOR FOR
SELECT DEPT_NO
INTO :wellpaid
FROM DEPARTMENT
WHERE SALARY > (SELECT AVG(SALARY) FROM DEPARTMENT);

)RUPRUHLQIRUPDWLRQDERXWXVLQJVXETXHULHVWRVSHFLI\VHDUFKFRQGLWLRQVVHH´8VLQJ
VXETXHULHVµRQSDJH )RUPRUHLQIRUPDWLRQDERXWDJJUHJDWHIXQFWLRQVVHH´5HWULHYLQJ
DJJUHJDWHFROXPQLQIRUPDWLRQµRQSDJH 

Using the string operator in expressions


7KHVWULQJRSHUDWRU__DOVRUHIHUUHGWRDVDFRQFDWHQDWLRQRSHUDWRUHQDEOHVDVLQJOHFKDUDFWHU
VWULQJWREHEXLOWIURPWZRRUPRUHFKDUDFWHUVWULQJV&KDUDFWHUVWULQJVFDQEHFRQVWDQWVRU
YDOXHVUHWULHYHGIURPDFROXPQ)RUH[DPSOH
char strbuf[80];
. . .
EXEC SQL
SELECT LAST_NAME || " is the manager of publications."
INTO :strbuf
FROM DEPARTMENT, EMPLOYEE
WHERE DEPT_NO = 5900 AND MNGR_NO = EMP_NO;

7KHVWULQJRSHUDWRUFDQDOVREHXVHGLQ,16(57RU83'$7(VWDWHPHQWV
EXEC SQL
INSERT INTO DEPARTMENT (MANAGER_NAME)
VALUES(:fname || :lname);

92 INTERBASE 5
UNDERSTANDING SQL EXPRESSIONS

Using arithmetic operators in expressions


7RFDOFXODWHQXPHULFYDOXHVLQH[SUHVVLRQV,QWHU%DVHUHFRJQL]HVIRXUDULWKPHWLFRSHUDWRUV
OLVWHGLQWKHIROORZLQJWDEOH

Precedenc Precedenc
Operator Purpose e Operator Purpose e
* Multiplication 1 + Addition 3
/ Division 2 – Subtraction 4
TABLE 6.3 Arithmetic operators

$ULWKPHWLFRSHUDWRUVDUHHYDOXDWHGIURPOHIWWRULJKWH[FHSWZKHQDPELJXLWLHVDULVH,QWKHVH
FDVHV,QWHU%DVHHYDOXDWHVRSHUDWLRQVDFFRUGLQJWRWKHSUHFHGHQFHVSHFLILHGLQWKHWDEOH IRU
H[DPSOHPXOWLSOLFDWLRQVDUHSHUIRUPHGEHIRUHGLYLVLRQVDQGGLYLVLRQVDUHSHUIRUPHGEHIRUH
VXEWUDFWLRQV 
$ULWKPHWLFRSHUDWLRQVDUHDOZD\VFDOFXODWHGEHIRUHFRPSDULVRQDQGORJLFDORSHUDWLRQV7R
FKDQJHRUIRUFHWKHRUGHURIHYDOXDWLRQJURXSRSHUDWLRQVLQSDUHQWKHVHV,QWHU%DVHFDOFXODWHV
RSHUDWLRQVZLWKLQSDUHQWKHVHVILUVW,ISDUHQWKHVHVDUHQHVWHGWKHHTXDWLRQLQWKHLQQHUPRVW
VHWLVWKHILUVWHYDOXDWHGDQGWKHRXWHUPRVWVHWLVHYDOXDWHGODVW)RUPRUHLQIRUPDWLRQDERXW
SUHFHGHQFHDQGXVLQJSDUHQWKHVHVIRUJURXSLQJVHH´'HWHUPLQLQJSUHFHGHQFHRIRSHUDWRUVµ
RQSDJH 
7KHIROORZLQJH[DPSOHLOOXVWUDWHVD:+(5(FODXVHVHDUFKFRQGLWLRQWKDWXVHVDQDULWKPHWLF
RSHUDWRUWRFRPELQHWKHYDOXHVIURPWZRFROXPQVWKHQXVHVDFRPSDULVRQRSHUDWRUWR
GHWHUPLQHLIWKDWYDOXHLVJUHDWHUWKDQ
DECLARE RAINCITIES CURSOR FOR
SELECT CITYNAME, COUNTRYNAME
INTO :cityname, :countryname
FROM CITIES
WHERE JANUARY_RAIN + FEBRUARY_RAIN > 10;

Using logical operators in expressions


/RJLFDORSHUDWRUVFDOFXODWHD%RROHDQYDOXH7UXH)DOVHRU8QNQRZQEDVHGRQFRPSDULQJ
SUHYLRXVO\FDOFXODWHGVLPSOHVHDUFKFRQGLWLRQVLPPHGLDWHO\WRWKHOHIWDQGULJKWRIWKH
RSHUDWRU,QWHU%DVHUHFRJQL]HVWKUHHORJLFDORSHUDWRUV127$1'DQG25

PROGRAMMER’S GUIDE 93
CHAPTER 6 WORKING WITH DATA

127UHYHUVHVWKHVHDUFKFRQGLWLRQLQZKLFKLWDSSHDUVZKLOH$1'DQG25DUHXVHGWR
FRPELQHVLPSOHVHDUFKFRQGLWLRQV)RUH[DPSOHWKHIROORZLQJTXHU\UHWXUQVDQ\HPSOR\HH
ZKRVHODVWQDPHLVQRW´6PLWKµ
DECLARE NOSMITH CURSOR FOR
SELECT LAST_NAME
INTO :lname
FROM EMPLOYEE
WHERE NOT LNAME = "Smith";

:KHQ$1'DSSHDUVEHWZHHQVHDUFKFRQGLWLRQVERWKVHDUFKFRQGLWLRQVPXVWEHWUXHLIDURZ
LVWREHUHWULHYHG7KHIROORZLQJTXHU\UHWXUQVDQ\HPSOR\HHZKRVHODVWQDPHLVQHLWKHU
´6PLWKµQRU´-RQHVµ
DECLARE NO_SMITH_OR_JONES CURSOR FOR
SELECT LAST_NAME
INTO :lname
FROM EMPLOYEE
WHERE NOT LNAME = "Smith" AND NOT LNAME = "Jones";

25VWLSXODWHVWKDWRQHVHDUFKFRQGLWLRQRUWKHRWKHUPXVWEHWUXH)RUH[DPSOHWKHIROORZLQJ
TXHU\UHWXUQVDQ\HPSOR\HHQDPHG´6PLWKµRU´-RQHVµ
DECLARE ALL_SMITH_JONES CURSOR FOR
SELECT LAST_NAME, FIRST_NAME
INTO :lname, :fname
FROM EMPLOYEE
WHERE LNAME = "Smith" OR LNAME = "Jones";

7KHRUGHULQZKLFKFRPELQHGVHDUFKFRQGLWLRQVDUHHYDOXDWHGLVGLFWDWHGE\WKHSUHFHGHQFH
RIWKHRSHUDWRUVWKDWFRQQHFWWKHP$127FRQGLWLRQLVHYDOXDWHGEHIRUH$1'DQG$1'LV
HYDOXDWHGEHIRUH253DUHQWKHVHVFDQEHXVHGWRFKDQJHWKHRUGHURIHYDOXDWLRQ)RUPRUH
LQIRUPDWLRQDERXWSUHFHGHQFHDQGXVLQJSDUHQWKHVHVIRUJURXSLQJVHH´'HWHUPLQLQJ
SUHFHGHQFHRIRSHUDWRUVµRQSDJH 

Using comparison operators in expressions


&RPSDULVRQRSHUDWRUVHYDOXDWHWRD%RROHDQYDOXH7UXH)DOVHRU8QNQRZQEDVHGRQDWHVW
IRUDVSHFLILFUHODWLRQVKLSEHWZHHQDYDOXHWRWKHOHIWRIWKHRSHUDWRUDQGDYDOXHRUUDQJHRI
YDOXHVWRWKHULJKWRIWKHRSHUDWRU9DOXHVFRPSDUHGPXVWHYDOXDWHWRWKHVDPHGDWDW\SH
XQOHVVWKH&$67 IXQFWLRQLVXVHGWRWUDQVODWHRQHGDWDW\SHWRDGLIIHUHQWRQHIRUFRPSDULVRQ
9DOXHVFDQEHFROXPQVFRQVWDQWVRUFDOFXODWHGYDOXHV
7KHIROORZLQJWDEOHOLVWVRSHUDWRUVWKDWFDQEHXVHGLQVWDWHPHQWVGHVFULEHVKRZWKH\DUH
XVHGDQGSURYLGHVVDPSOHVRIWKHLUXVH

94 INTERBASE 5
UNDERSTANDING SQL EXPRESSIONS

Note &RPSDULVRQVHYDOXDWHWR8QNQRZQLID18//YDOXHLVHQFRXQWHUHG
)RUPRUHLQIRUPDWLRQDERXW&$67 VHH´8VLQJ&$67 IRUGDWDW\SHFRQYHUVLRQVµRQ
SDJH 
,QWHU%DVHDOVRVXSSRUWVFRPSDULVRQRSHUDWRUVWKDWFRPSDUHDYDOXHRQWKHOHIWRIWKH
RSHUDWRUWRWKHUHVXOWVRIDVXETXHU\WRWKHULJKWRIWKHRSHUDWRU7KHIROORZLQJWDEOHOLVWV
WKHVHRSHUDWRUVDQGGHVFULEHVKRZWKH\DUHXVHG

Operator Purpose
ALL Determines if a value is equal to all values returned by a subquery.
ANY and SOME Determines if a value is equal to any values returned by a subquery.
EXISTS Determines if a value exists in at least one value returned by a subquery.
SINGULAR Determines if a value exists in exactly one value returned by a subquery.
TABLE 6.4 InterBase comparison operators requiring subqueries

)RUPRUHLQIRUPDWLRQDERXWXVLQJVXETXHULHVVHH´8VLQJVXETXHULHVµRQSDJH 

4 8VLQJ%(7:((1
%(7:((1WHVWVZKHWKHUDYDOXHIDOOVZLWKLQDUDQJHRIYDOXHV7KHFRPSOHWHV\QWD[IRUWKH
%(7:((1RSHUDWRULV
<value> [NOT] BETWEEN <value> AND <value>

)RUH[DPSOHWKHIROORZLQJFXUVRUGHFODUDWLRQUHWULHYHV/$67B1$0(DQG),567B1$0(
FROXPQVIRUHPSOR\HHVZLWKVDODULHVEHWZHHQDQGLQFOXVLYH
EXEC SQL
DECLARE LARGE_SALARIES CURSOR FOR
SELECT LAST_NAME, FIRST_NAME
FROM EMPLOYEE
WHERE SALARY BETWEEN 100000 AND 250000;

8VH127%(7:((1WRWHVWZKHWKHUDYDOXHIDOOVRXWVLGHDUDQJHRIYDOXHV)RUH[DPSOHWKH
IROORZLQJFXUVRUGHFODUDWLRQUHWULHYHVWKHQDPHVRIHPSOR\HHVZLWKVDODULHVOHVVWKDQ
DQGJUHDWHUWKDQ
EXEC SQL
DECLARE EXTREME_SALARIES CURSOR FOR
SELECT LAST_NAME, FIRST_NAME
FROM EMPLOYEE
WHERE SALARY NOT BETWEEN 30000 AND 150000;

PROGRAMMER’S GUIDE 95
CHAPTER 6 WORKING WITH DATA

4 8VLQJ&217$,1,1*
&217$,1,1*WHVWVWRVHHLIDQ$6&,,VWULQJYDOXHFRQWDLQVDTXRWHG$6&,,VWULQJVXSSOLHG
E\WKHSURJUDP6WULQJFRPSDULVRQVDUHFDVHLQVHQVLWLYH´6WULQJµ´675,1*µDQG´VWULQJµ
DUHHTXLYDOHQWYDOXHVIRU&217$,1,1*7KHFRPSOHWHV\QWD[IRU&217$,1,1*LV
<value> [NOT] CONTAINING "<string>"

)RUH[DPSOHWKHIROORZLQJFXUVRUGHFODUDWLRQUHWULHYHVWKHQDPHVRIDOOHPSOR\HHVZKRVHODVW
QDPHVFRQWDLQWKHWKUHHOHWWHUFRPELQDWLRQ´ODVµ DQG´/$6µRU´/DVµ 
EXEC SQL
DECLARE LAS_EMP CURSOR FOR
SELECT LAST_NAME, FIRST_NAME
FROM EMPLOYEE
WHERE LAST_NAME CONTAINING "las";

8VH127&217$,1,1*WRWHVWIRUVWULQJVWKDWH[FOXGHDVSHFLILHGYDOXH)RUH[DPSOHWKH
IROORZLQJFXUVRUGHFODUDWLRQUHWULHYHVWKHQDPHVRIDOOHPSOR\HHVZKRVHODVWQDPHVGRQRW
FRQWDLQ´ODVµ DOVR´/$6µRU´/DVµ 
EXEC SQL
DECLARE NOT_LAS_EMP CURSOR FOR
SELECT LAST_NAME, FIRST_NAME
FROM EMPLOYEE
WHERE LAST_NAME NOT CONTAINING "las";

7,3 &217$,1,1*FDQEHXVHGWRVHDUFKD%OREVHJPHQWE\VHJPHQWIRUDQRFFXUUHQFHRID
TXRWHGVWULQJ

4 8VLQJ,1
,1WHVWVWKDWDNQRZQYDOXHHTXDOVDWOHDVWRQHYDOXHLQDOLVWRIYDOXHV$OLVWLVDVHWRIYDOXHV
VHSDUDWHGE\FRPPDVDQGHQFORVHGE\SDUHQWKHVHV7KHYDOXHVLQWKHOLVWPXVWEH
SDUHQWKHVL]HGDQGVHSDUDWHGE\FRPPDV,IWKHYDOXHEHLQJFRPSDUHGWRDOLVWRIYDOXHVLV
18//,1UHWXUQV8QNQRZQ
7KHV\QWD[IRU,1LV
<value> [NOT] IN (<value> [, <value> ...])

)RUH[DPSOHWKHIROORZLQJFXUVRUGHFODUDWLRQUHWULHYHVWKHQDPHVRIDOOHPSOR\HHVLQWKH
DFFRXQWLQJSD\UROODQGKXPDQUHVRXUFHVGHSDUWPHQWV
EXEC SQL
DECLARE ACCT_PAY_HR CURSOR FOR
SELECT DEPARTMENT, LAST_NAME, FIRST_NAME, EMP_NO
FROM EMPLOYEE EMP, DEPTARTMENT DEP

96 INTERBASE 5
UNDERSTANDING SQL EXPRESSIONS

WHERE EMP.DEPT_NO = DEP.DEPT_NO AND


DEPARTMENT IN ("Accounting", "Payroll", "Human Resources")
GROUP BY DEPARTMENT;

8VH127,1WRWHVWWKDWDYDOXHGRHVQRWRFFXULQDVHWRIVSHFLILHGYDOXHV)RUH[DPSOHWKH
IROORZLQJFXUVRUGHFODUDWLRQUHWULHYHVWKHQDPHVRIDOOHPSOR\HHVQRWLQWKHDFFRXQWLQJ
SD\UROODQGKXPDQUHVRXUFHVGHSDUWPHQWV
EXEC SQL
DECLARE NOT_ACCT_PAY_HR CURSOR FOR
SELECT DEPARTMENT, LAST_NAME, FIRST_NAME, EMP_NO
FROM EMPLOYEE EMP, DEPTARTMENT DEP
WHERE EMP.DEPT_NO = DEP.DEPT_NO AND
DEPARTMENT NOT IN ("Accounting", "Payroll",
"Human Resources")
GROUP BY DEPARTMENT;

,1FDQDOVREHXVHGWRFRPSDUHDYDOXHDJDLQVWWKHUHVXOWVRIDVXETXHU\)RUH[DPSOHWKH
IROORZLQJFXUVRUGHFODUDWLRQUHWULHYHVDOOFLWLHVLQ(XURSH
EXEC SQL
DECLARE NON_JFG_CITIES CURSOR FOR
SELECT C.COUNTRY, C.CITY, C.POPULATION
FROM CITIES C
WHERE C.COUNTRY NOT IN (SELECT O.COUNTRY FROM COUNTRIES O
WHERE O.CONTINENT <> "Europe")
GROUP BY C.COUNTRY;

)RUPRUHLQIRUPDWLRQDERXWVXETXHULHVVHH´8VLQJVXETXHULHVµRQSDJH 

4 8VLQJ/,.(
/,.(LVDFDVHVHQVLWLYHRSHUDWRUWKDWWHVWVDVWULQJYDOXHDJDLQVWDVWULQJFRQWDLQLQJZLOGFDUGV
V\PEROVWKDWVXEVWLWXWHIRUDVLQJOHYDULDEOHFKDUDFWHURUDVWULQJRIYDULDEOHFKDUDFWHUV/,.(
UHFRJQL]HVWZRZLOGFDUGV\PEROV
g  SHUFHQW VXEVWLWXWHVIRUDVWULQJRI]HURRUPRUHFKDUDFWHUV
g B XQGHUVFRUH VXEVWLWXWHVIRUDVLQJOHFKDUDFWHU
7KHV\QWD[IRU/,.(LV
<value> [NOT] LIKE <value> [ESCAPE "symbol"]

)RUH[DPSOHWKLVFXUVRUUHWULHYHVLQIRUPDWLRQDERXWDQ\HPSOR\HHZKRVHODVWQDPHVFRQWDLQ
WKHWKUHHOHWWHUFRPELQDWLRQ´WRQµ EXWQRW´7RQµ 
EXEC SQL
DECLARE TON_EMP CURSOR FOR

PROGRAMMER’S GUIDE 97
CHAPTER 6 WORKING WITH DATA

SELECT LAST_NAME, FIRST_NAME, EMP_NO


FROM EMPLOYEE
WHERE LAST_NAME LIKE "%ton%";

7RWHVWIRUDVWULQJWKDWFRQWDLQVDSHUFHQWRUXQGHUVFRUHFKDUDFWHU
 3UHFHGHWKH RUBZLWKDQRWKHUV\PERO IRUH[DPSOH# LQWKHTXRWHG
FRPSDULVRQVWULQJ
 8VHWKH(6&$3(FODXVHWRLGHQWLI\WKHV\PERO #LQWKLVFDVH SUHFHGLQJ RU
BDVDOLWHUDOV\PERO$OLWHUDOV\PEROWHOOV,QWHU%DVHWKDWWKHQH[WFKDUDFWHUVKRXOG
EHLQFOXGHGDVLVLQWKHVHDUFKVWULQJ
)RUH[DPSOHWKLVFXUVRUUHWULHYHVDOOWDEOHQDPHVLQ5'%5(/$7,216WKDWKDYHXQGHUVFRUHV
LQWKHLUQDPHV
EXEC SQL
DECLARE UNDER_TABLE CURSOR FOR
SELECT RDB$RELATION_NAME
FROM RDB$RELATIONS
WHERE RDB$RELATION_NAME LIKE "%@_%" ESCAPE "@";

8VH127/,.(WRUHWULHYHURZVWKDWGRQRWFRQWDLQVWULQJVPDWFKLQJWKRVHGHVFULEHG)RU
H[DPSOHWKHIROORZLQJFXUVRUUHWULHYHVDOOWDEOHQDPHVLQ5'%5(/$7,216WKDWGRQRWKDYH
XQGHUVFRUHVLQWKHLUQDPHV
EXEC SQL
DECLARE NOT_UNDER_TABLE CURSOR FOR
SELECT RDB$RELATION_NAME
FROM RDB$RELATIONS
WHERE RDB$RELATION_NAME NOT LIKE "%@_%" ESCAPE "@";

4 8VLQJ,618//
,618//WHVWVIRUWKHDEVHQFHRIDYDOXHLQDFROXPQ7KHFRPSOHWHV\QWD[RIWKH,618//
FODXVHLV
<value> IS [NOT] NULL

)RUH[DPSOHWKHIROORZLQJFXUVRUUHWULHYHVWKHQDPHVRIHPSOR\HHVZKRGRQRWKDYHSKRQH
H[WHQVLRQV
EXEC SQL
DECLARE MISSING_PHONE CURSOR FOR
SELECT LAST_NAME, FIRST_NAME
FROM EMPLOYEE
WHERE PHONE_EXT IS NULL;
8VH,612718//WRWHVWWKDWDFROXPQFRQWDLQVDYDOXH)RUH[DPSOHWKHIROORZLQJFXUVRU
UHWULHYHVWKHSKRQHQXPEHUVRIDOOHPSOR\HHVWKDWKDYHSKRQHH[WHQVLRQV

98 INTERBASE 5
UNDERSTANDING SQL EXPRESSIONS

EXEC SQL
DECLARE PHONE_LIST CURSOR FOR
SELECT LAST_NAME, FIRST_NAME, PHONE_EXT
FROM EMPLOYEE
WHERE PHONE_EXT IS NOT NULL
ORDER BY LAST_NAME, FIRST_NAME;

4 8VLQJ67$57,1*:,7+
67$57,1*:,7+LVDFDVHVHQVLWLYHRSHUDWRUWKDWWHVWVDVWULQJYDOXHWRVHHLILWEHJLQVZLWKD
VWLSXODWHGVWULQJRIFKDUDFWHUV7RVXSSRUWLQWHUQDWLRQDOFKDUDFWHUVHWFRQYHUVLRQV67$57,1*
:,7+IROORZVE\WHPDWFKLQJUXOHVIRUWKHVSHFLILHGFROODWLRQRUGHU7KHFRPSOHWHV\QWD[IRU
67$57,1*:,7+LV
<value> [NOT] STARTING WITH <value>

)RUH[DPSOHWKHIROORZLQJFXUVRUUHWULHYHVHPSOR\HHODVWQDPHVWKDWVWDUWZLWK´7Rµ
EXEC SQL
DECLARE TO_EMP CURSOR FOR
SELECT LAST_NAME, FIRST_NAME
FROM EMPLOYEE
WHERE LAST_NAME STARTING WITH "To";

8VH12767$57,1*:,7+WRUHWULHYHLQIRUPDWLRQIRUFROXPQVWKDWGRQRWEHJLQZLWKWKH
VWLSXODWHGVWULQJ)RUH[DPSOHWKHIROORZLQJFXUVRUUHWULHYHVDOOHPSOR\HHVH[FHSWWKRVH
ZKRVHODVWQDPHVVWDUWZLWK´7Rµ
EXEC SQL
DECLARE NOT_TO_EMP CURSOR FOR
SELECT LAST_NAME, FIRST_NAME
FROM EMPLOYEE
WHERE LAST_NAME NOT STARTING WITH "To";

)RUPRUHLQIRUPDWLRQDERXWFROODWLRQRUGHUDQGE\WHPDWFKLQJUXOHVVHHWKH'DWD'HILQLWLRQ
*XLGH

4 8VLQJ$//
$//WHVWVWKDWDYDOXHLVWUXHZKHQFRPSDUHGWRHYHU\YDOXHLQDOLVWUHWXUQHGE\DVXETXHU\
7KHFRPSOHWHV\QWD[IRU$//LV
<value> <comparison_operator> ALL (<subquery>)

)RUH[DPSOHWKHIROORZLQJFXUVRUUHWULHYHVLQIRUPDWLRQDERXWHPSOR\HHVZKRVHVDODULHVDUH
ODUJHUWKDQWKDWRIWKHYLFHSUHVLGHQWRIFKDQQHOPDUNHWLQJ
EXEC SQL
DECLARE MORE_THAN_VP CURSOR FOR

PROGRAMMER’S GUIDE 99
CHAPTER 6 WORKING WITH DATA

SELECT LAST_NAME, FIRST_NAME, SALARY


FROM EMPLOYEE
WHERE SALARY > ALL (SELECT SALARY FROM EMPLOYEE
WHERE DEPT_NO = 7734);

$//UHWXUQV8QNQRZQLIWKHVXETXHU\UHWXUQVD18//YDOXH,WFDQDOVRUHWXUQ8QNQRZQLI
WKHYDOXHWREHFRPSDUHGLV18//DQGWKHVXETXHU\UHWXUQVDQ\QRQ18//GDWD,IWKHYDOXH
LV18//DQGWKHVXETXHU\UHWXUQVDQHPSW\VHW$//HYDOXDWHVWR7UXH
)RUPRUHLQIRUPDWLRQDERXWVXETXHULHVVHH´8VLQJVXETXHULHVµRQSDJH 

4 8VLQJ$1<DQG620(
$1<DQG620(WHVWWKDWDYDOXHLVWUXHLILWPDWFKHVDQ\YDOXHLQDOLVWUHWXUQHGE\DVXETXHU\
7KHFRPSOHWHV\QWD[IRU$1<LV
<value> <comparison_operator> ANY | SOME (<subquery>)

)RUH[DPSOHWKHIROORZLQJFXUVRUUHWULHYHVLQIRUPDWLRQDERXWVDODULHVWKDWDUHODUJHUWKDQDW
OHDVWRQHVDODU\LQWKHFKDQQHOPDUNHWLQJGHSDUWPHQW
EXEC SQL
DECLARE MORE_CHANNEL CURSOR FOR
SELECT LAST_NAME, FIRST_NAME, SALARY
FROM EMPLOYEE
WHERE SALARY > ANY (SELECT SALARY FROM EMPLOYEE
WHERE DEPT_NO = 7734);

$1<DQG620(UHWXUQ8QNQRZQLIWKHVXETXHU\UHWXUQVD18//YDOXH7KH\FDQDOVRUHWXUQ
8QNQRZQLIWKHYDOXHWREHFRPSDUHGLV18//DQGWKHVXETXHU\UHWXUQVDQ\QRQ18//GDWD
,IWKHYDOXHLV18//DQGWKHVXETXHU\UHWXUQVDQHPSW\VHW$1<DQG620(HYDOXDWHWR)DOVH
)RUPRUHLQIRUPDWLRQDERXWVXETXHULHVVHH´8VLQJVXETXHULHVµRQSDJH 

4 8VLQJ(;,676
(;,676WHVWVWKDWIRUDJLYHQYDOXHWKHUHLVDWOHDVWRQHTXDOLI\LQJURZPHHWLQJWKHVHDUFK
FRQGLWLRQVSHFLILHGLQDVXETXHU\7KH6(/(&7FODXVHLQWKHVXETXHU\PXVWXVHWKH 
DVWHULVN WRVHOHFWDOOFROXPQV7KHFRPSOHWHV\QWD[IRU(;,676LV
[NOT] EXISTS (SELECT * FROM <tablelist> WHERE <search_condition>)

7KHIROORZLQJFXUVRUUHWULHYHVDOOFRXQWULHVZLWKULYHUV
EXEC SQL
DECLARE RIVER_COUNTRIES CURSOR FOR
SELECT COUNTRY
FROM COUNTRIES C

100 INTERBASE 5
UNDERSTANDING SQL EXPRESSIONS

WHERE EXISTS (SELECT * FROM RIVERS R


WHERE R.COUNTRY = C.COUNTRY);

8VH127(;,676WRUHWULHYHURZVWKDWGRQRWPHHWWKHTXDOLI\LQJFRQGLWLRQVSHFLILHGLQWKH
VXETXHU\7KHIROORZLQJFXUVRUUHWULHYHVDOOFRXQWULHVZLWKRXWULYHUV
EXEC SQL
DECLARE NON_RIVER_COUNTRIES COUNTRIES FOR
SELECT COUNTRY
FROM COUNTRIES C
WHERE NOT EXISTS (SELECT * FROM RIVERS R
WHERE R.COUNTRY = C.COUNTRY);

(;,676DOZD\VUHWXUQVHLWKHU7UXHRU)DOVHHYHQZKHQKDQGOLQJ18//YDOXHV
)RUPRUHLQIRUPDWLRQDERXWVXETXHULHVVHH´8VLQJVXETXHULHVµRQSDJH 

4 8VLQJ6,1*8/$5
6,1*8/$5WHVWVWKDWIRUDJLYHQYDOXHWKHUHLVH[DFWO\RQHTXDOLI\LQJURZPHHWLQJWKHVHDUFK
FRQGLWLRQVSHFLILHGLQDVXETXHU\7KH6(/(&7FODXVHLQWKHVXETXHU\PXVWXVHWKH 
DVWHULVN WRVHOHFWDOOFROXPQV7KHFRPSOHWHV\QWD[IRU6,1*8/$5LV
[NOT] SINGULAR (SELECT * FROM <tablelist> WHERE <search_condition>)

7KHIROORZLQJFXUVRUUHWULHYHVDOOFRXQWULHVZLWKDVLQJOHFDSLWDO
EXEC SQL
DECLARE SINGLE_CAPITAL CURSOR FOR
SELECT COUNTRY
FROM COUNTRIES COU
WHERE SINGULAR (SELECT * FROM CITIES CIT
WHERE CIT.CITY = COU.CAPITAL);

8VH1276,1*8/$5WRUHWULHYHURZVWKDWGRQRWPHHWWKHTXDOLI\LQJFRQGLWLRQVSHFLILHGLQ
WKHVXETXHU\)RUH[DPSOHWKHIROORZLQJFXUVRUUHWULHYHVDOOFRXQWULHVZLWKPRUHWKDQRQH
FDSLWDO
EXEC SQL
DECLARE MULTI_CAPITAL CURSOR FOR
SELECT COUNTRY
FROM COUNTRIES COU
WHERE NOT SINGULAR (SELECT * FROM CITIES CIT
WHERE CIT.CITY = COU.CAPITAL);

)RUPRUHLQIRUPDWLRQDERXWVXETXHULHVVHH´8VLQJVXETXHULHVµRQSDJH 

PROGRAMMER’S GUIDE 101


CHAPTER 6 WORKING WITH DATA

Determining precedence of operators


7KHRUGHULQZKLFKRSHUDWRUVDQGWKHYDOXHVWKH\DIIHFWDUHHYDOXDWHGLQDVWDWHPHQWLVFDOOHG
SUHFHGHQFH7KHUHDUHWZROHYHOVRISUHFHGHQFHIRU64/RSHUDWRUV
g 3UHFHGHQFHDPRQJRSHUDWRUVRIGLIIHUHQWW\SHV
g 3UHFHGHQFHDPRQJRSHUDWRUVRIWKHVDPHW\SH

4 3UHFHGHQFHDPRQJRSHUDWRUV
AMONG OPERATORS OF DIFFERENT TYPES
7KHIROORZLQJWDEOHOLVWVWKHHYDOXDWLRQRUGHURIGLIIHUHQW,QWHU%DVHRSHUDWRUW\SHVIURPILUVW
HYDOXDWHG KLJKHVWSUHFHGHQFH WRODVWHYDOXDWHG ORZHVWSUHFHGHQFH 

Operator type Precedence Explanation


String Highest Strings are always concatenated before all other operations take
place.
Mathematical ? Math is performed after string concatenation, but before
comparison and logical operations.
Comparison ? Comparison operations are evaluated after string concatenation
and math, but before logical operations.
Logical Lowest Logical operations are evaluated after all other operations.
TABLE 6.5 Operator precedence by operator type

AMONG OPERATORS OF THE SAME TYPE


:KHQDQH[SUHVVLRQFRQWDLQVVHYHUDORSHUDWRUVRIWKHVDPHW\SHWKRVHRSHUDWRUVDUH
HYDOXDWHGIURPOHIWWRULJKWXQOHVVWKHUHLVDFRQIOLFWZKHUHWZRRSHUDWRUVRIWKHVDPHW\SH
DIIHFWWKHVDPHYDOXHV
)RUH[DPSOHLQWKHPDWKHPDWLFDOHTXDWLRQ ERWKWKHDGGLWLRQDQGPXOWLSOLFDWLRQ
RSHUDWRUVZRUNZLWKWKHVDPHYDOXH(YDOXDWHGIURPOHIWWRULJKWWKHHTXDWLRQHYDOXDWHVWR
   ,QWHU%DVHIROORZVVWDQGDUGPDWKHPDWLFDOUXOHVIRUHYDOXDWLQJ
PDWKHPDWLFDOH[SUHVVLRQVWKDWVWLSXODWHPXOWLSOLFDWLRQLVSHUIRUPHGEHIRUHDGGLWLRQ  
 

102 INTERBASE 5
UNDERSTANDING SQL EXPRESSIONS

7KHIROORZLQJWDEOHOLVWVWKHHYDOXDWLRQRUGHUIRUDOOPDWKHPDWLFDORSHUDWRUVIURPKLJKHVWWR
ORZHVW

Operator Precedence Explanation


* Highest Multiplication is performed before all other mathematical operations.
/ ? Division is performed before addition and subtraction.
+ ? Addition is performed before subtraction.
– Lowest Subtraction is performed after all other mathematical operations.
TABLE 6.6 Mathematical operator precedence

,QWHU%DVHDOVRIROORZVUXOHVIRUGHWHUPLQLQJWKHRUGHULQZKLFKFRPSDULVRQRSHUDWRUVDUH
HYDOXDWHGZKHQFRQIOLFWVDULVHGXULQJQRUPDOOHIWWRULJKWHYDOXDWLRQ7KHQH[WWDEOHGHVFULEHV
WKHHYDOXDWLRQRUGHUIRUFRPSDULVRQRSHUDWRUVIURPKLJKHVWWRORZHVW

Operator Precedence Explanation


=, == Highest Equality operations are evaluated before all other
comparison operations.
<>, !=, ~=, ^= ?
> ?
< ?
>= ?
<= ?
!>, ~>, ^> ?
!<, ~<, ^< Lowest Not less than operations are evaluated after all other
comparison operations.
TABLE 6.7 Comparison operator precedence

$//$1<%(7:((1&217$,1,1*(;,676,1/,.(18//6,1*8/$5620(DQG
67$57,1*:,7+DUHHYDOXDWHGDIWHUDOOOLVWHGFRPSDULVRQRSHUDWRUVZKHQWKH\FRQIOLFWZLWK
RWKHUFRPSDULVRQRSHUDWRUVGXULQJQRUPDOOHIWWRULJKWHYDOXDWLRQ:KHQWKH\FRQIOLFWZLWK
RQHDQRWKHUWKH\DUHHYDOXDWHGVWULFWO\IURPOHIWWRULJKW

PROGRAMMER’S GUIDE 103


CHAPTER 6 WORKING WITH DATA

:KHQORJLFDORSHUDWRUVFRQIOLFWGXULQJQRUPDOOHIWWRULJKWSURFHVVLQJWKH\WRRDUHHYDOXDWHG
DFFRUGLQJWRDKLHUDUFK\GHWDLOHGLQWKHIROORZLQJWDEOH

Operator Precedence Explanation


NOT Highest NOT operations are evaluated before all other logical operations.
AND ? AND operations are evaluated after NOT operations, and before OR
operations.
OR Lowest OR operations are evaluated after all other logical operations.
TABLE 6.8 Logical operator precedence

4 &KDQJLQJHYDOXDWLRQRUGHURIRSHUDWRUV
7RFKDQJHWKHHYDOXDWLRQRUGHURIRSHUDWLRQVLQDQH[SUHVVLRQXVHSDUHQWKHVHVWRJURXS
RSHUDWLRQVWKDWVKRXOGEHHYDOXDWHGDVDXQLWRUWKDWVKRXOGGHULYHDVLQJOHYDOXHIRUXVHLQ
RWKHURSHUDWLRQV)RUH[DPSOHZLWKRXWSDUHQWKHWLFDOJURXSLQJ HYDOXDWHVWR7R
FDXVHWKHDGGLWLRQWREHSHUIRUPHGEHIRUHWKHPXOWLSOLFDWLRQXVHSDUHQWKHVHV
(3 + 2) * 6 = 30

7,3 $OZD\VXVHSDUHQWKHVHVWRJURXSRSHUDWLRQVLQFRPSOH[H[SUHVVLRQVHYHQZKHQGHIDXOW
RUGHURIHYDOXDWLRQLVGHVLUHG([SOLFLWO\JURXSHGH[SUHVVLRQVDUHHDVLHUWRXQGHUVWDQGDQG
GHEXJ

Using CAST() for datatype conversions


1RUPDOO\RQO\VLPLODUGDWDW\SHVFDQEHFRPSDUHGRUHYDOXDWHGLQH[SUHVVLRQV7KH&$67 
IXQFWLRQFDQEHXVHGLQH[SUHVVLRQVWRWUDQVODWHRQHGDWDW\SHLQWRDQRWKHUIRUFRPSDULVRQ
SXUSRVHV7KHV\QWD[IRU&$67 LV
CAST (<value> | NULL AS datatype)

)RUH[DPSOHLQWKHIROORZLQJ:+(5(FODXVH&$67 LVXVHGWRWUDQVODWHD&+$5GDWDW\SH
,17(59,(:B'$7(WRD'$7(GDWDW\SHWRFRPSDUHDJDLQVWD'$7(GDWDW\SH+,5(B'$7(
WHERE HIRE_DATE = CAST(INTERVIEW_DATE AS DATE);

104 INTERBASE 5
UNDERSTANDING SQL EXPRESSIONS

&$67 FDQEHXVHGWRFRPSDUHFROXPQVZLWKGLIIHUHQWGDWDW\SHVLQWKHVDPHWDEOHRUDFURVV
WDEOHV<RXFDQFRQYHUWRQHGDWDW\SHWRDQRWKHUDVVKRZQLQWKHIROORZLQJWDEOH

From datatype To datatype


NUMERIC CHARACTER, DATE

CHARACTER NUMERIC, DATE

DATE CHARACTER, NUMERIC

TABLE 6.9 Compatible datatypes for CAST()

$QHUURUUHVXOWVLIDJLYHQGDWDW\SHFDQQRWEHFRQYHUWHGLQWRWKHGDWDW\SHVSHFLILHGLQ&$67 

Using UPPER() on text data


7KH833(5 IXQFWLRQFDQEHXVHGLQ6(/(&7,16(5783'$7(RU'(/(7(RSHUDWLRQVWR
IRUFHFKDUDFWHUDQG%OREWH[WGDWDWRXSSHUFDVH)RUH[DPSOHDQDSSOLFDWLRQWKDWSURPSWVD
XVHUIRUDGHSDUWPHQWQDPHPLJKWZDQWWRHQVXUHWKDWDOOGHSDUWPHQWQDPHVDUHVWRUHGLQ
XSSHUFDVHWRVLPSOLI\GDWDUHWULHYDOODWHU7KHIROORZLQJFRGHLOOXVWUDWHVKRZ833(5 ZRXOG
EHXVHGLQWKH,16(57VWDWHPHQWWRJXDUDQWHHDXVHU·VHQWU\LVXSSHUFDVH
EXEC SQL
BEGIN DECLARE SECTION;
char response[26];
EXEC SQL
END DECLARE SECTION;
. . .
printf("Enter new department name: ");
response[0] = ’\0’;
gets(response);
if (response)
EXEC SQL
INSERT INTO DEPARTMENT(DEPT_NO, DEPARTMENT)
VALUES(GEN_ID(GDEPT_NO, 1), UPPER(:response));
. . .

7KHQH[WVWDWHPHQWLOOXVWUDWHVKRZ833(5 FDQEHXVHGLQD6(/(&7VWDWHPHQWWRDIIHFWERWK
WKHDSSHDUDQFHRIYDOXHVUHWULHYHGDQGWRDIIHFWLWVVHDUFKFRQGLWLRQ
EXEC SQL
SELECT DEPT_NO, UPPER(DEPARTMENT)
FROM DEPARTMENT
WHERE UPPER(DEPARTMENT) STARTING WITH ’A’;

PROGRAMMER’S GUIDE 105


CHAPTER 6 WORKING WITH DATA

Understanding data retrieval with SELECT


7KH6(/(&7VWDWHPHQWKDQGOHVDOOTXHULHVLQ64/6(/(&7FDQUHWULHYHRQHRUPRUHURZV
IURPDWDEOHDQGFDQUHWXUQHQWLUHURZVRUDVXEVHWRIFROXPQVIURPHDFKURZRIWHQUHIHUUHG
WRDVDSURMHFWLRQ2SWLRQDO6(/(&7V\QWD[FDQEHXVHGWRVSHFLI\VHDUFKFULWHULDWKDWUHVWULFW
WKHQXPEHURIURZVUHWXUQHGWRVHOHFWURZVZLWKXQNQRZQYDOXHVWRVHOHFWURZVWKURXJKD
YLHZDQGWRFRPELQHURZVIURPWZRRUPRUHWDEOHV
$WDPLQLPXPHYHU\6(/(&7VWDWHPHQWPXVW
g /LVWZKLFKFROXPQVWRUHWULHYHIURPDWDEOH7KHFROXPQOLVWLPPHGLDWHO\IROORZVWKH6(/(&7
NH\ZRUG
g 1DPHWKHWDEOHWRVHDUFKLQD)520FODXVH
6LQJOHWRQVHOHFWVPXVWDOVRLQFOXGHERWKDQ,172FODXVHWRVSHFLI\WKHKRVWYDULDEOHVLQWR
ZKLFKUHWULHYHGYDOXHVVKRXOGEHVWRUHGDQGD:+(5(FODXVHWRVSHFLI\WKHVHDUFKFRQGLWLRQV
WKDWFDXVHRQO\DVLQJOHURZWREHUHWXUQHG
7KHIROORZLQJ6(/(&7UHWULHYHVWKUHHFROXPQVIURPDWDEOHDQGVWRUHVWKHYDOXHVLQWKUHH
KRVWODQJXDJHYDULDEOHV
EXEC SQL
SELECT EMP_NO, FIRSTNAME, LASTNAME
INTO :emp_no, :fname, :lname
FROM EMPLOYEE WHERE EMP_NO = 1888;

7,3 +RVWYDULDEOHVPXVWEHGHFODUHGLQDSURJUDPEHIRUHWKH\FDQEHXVHGLQ64/VWDWHPHQWV
)RUPRUHLQIRUPDWLRQDERXWGHFODULQJKRVWYDULDEOHVVHH&KDSWHU´$SSOLFDWLRQ
5HTXLUHPHQWVµ
7KHIROORZLQJWDEOHOLVWVDOO6(/(&7VWDWHPHQWFODXVHVLQWKHRUGHUWKDWWKH\DUHXVHGDQG
SUHVFULEHVWKHLUXVHLQVLQJOHWRQDQGPXOWLURZVHOHFWV

Singleton Multi-row
Clause Purpose SELECT SELECT
SELECT Lists columns to retrieve. Required Required
INTO Lists host variables for storing retrieved columns. Required Not allowed
FROM Identifies the tables to search for values. Required Required
WHERE Specifies the search conditions used to restrict retrieved rows Optional Optional
to a subset of all available rows. A WHERE clause can contain its
own SELECT statement, referred to as a subquery.
TABLE 6.10 SELECT statement clauses

106 INTERBASE 5
UNDERSTANDING DATA RETRIEVAL WITH SELECT

Singleton Multi-row
Clause Purpose SELECT SELECT
GROUP BY Groups related rows based on common column values. Used in Optional Optional
conjunction with HAVING.
HAVING Restricts rows generated by GROUP BY to a subset of those rows. Optional Optional
UNION Combines the results of two or more SELECT statements to Optional Optional
produce a single, dynamic table without duplicate rows.
PLAN Specifies the query plan that should be used by the query Optional Optional
optimizer instead of one it would normally choose.
ORDER BY Specifies the sort order of rows returned by a SELECT, either Optional Optional
ascending (ASC), the default, or descending (DESC).
FOR UPDATE Specifies columns listed after the SELECT clause of a DECLARE Not allowed Optional
CURSOR statement that can be updated using a WHERE CURRENT
OF clause.

TABLE 6.10 SELECT statement clauses (continued)

8VLQJHDFKRIWKHVHFODXVHVZLWK6(/(&7LVGHVFULEHGLQWKHIROORZLQJVHFWLRQVDIWHUZKLFK
XVLQJ6(/(&7GLUHFWO\WRUHWXUQDVLQJOHURZDQGXVLQJ6(/(&7ZLWKLQD'(&/$5(&85625
VWDWHPHQWWRUHWXUQPXOWLSOHURZVDUHGHVFULEHGLQGHWDLO)RUDFRPSOHWHRYHUYLHZRI6(/(&7
V\QWD[VHHWKH/DQJXDJH5HIHUHQFH

Listing columns to retrieve with SELECT


$OLVWRIFROXPQVWRUHWULHYHPXVWDOZD\VIROORZWKH6(/(&7NH\ZRUGLQD6(/(&7VWDWHPHQW
7KH6(/(&7NH\ZRUGDQGLWVFROXPQOLVWLVFDOOHGD6(/(&7FODXVH

4 5HWULHYLQJDOLVWRIFROXPQV
7RUHWULHYHDVXEVHWRIFROXPQVIRUDURZRIGDWDOLVWHDFKFROXPQE\QDPHLQWKHRUGHURI
GHVLUHGUHWULHYDODQGVHSDUDWHHDFKFROXPQQDPHIURPWKHQH[WE\DFRPPD2SHUDWLRQVWKDW
UHWULHYHDVXEVHWRIFROXPQVDUHRIWHQFDOOHGSURMHFWLRQV
)RUH[DPSOHWKHIROORZLQJ6(/(&7UHWULHYHVWKUHHFROXPQV
EXEC SQL
SELECT EMP_NO, FIRSTNAME, LASTNAME
INTO :emp_no, :fname, :lname
FROM EMPLOYEE WHERE EMP_NO = 2220;

PROGRAMMER’S GUIDE 107


CHAPTER 6 WORKING WITH DATA

4 5HWULHYLQJDOOFROXPQV
7RUHWULHYHDOOFROXPQVRIGDWDXVHDQDVWHULVN LQVWHDGRIOLVWLQJDQ\FROXPQVE\QDPH)RU
H[DPSOHWKHIROORZLQJ6(/(&7UHWULHYHVHYHU\FROXPQRIGDWDIRUDVLQJOHURZLQWKH
(03/2<((WDEOH
EXEC SQL
SELECT *
INTO :emp_no, :fname, :lname, :phone_ext, :hire, :dept_no,
:job_code, :job_grade, :job_country, :salary, :full_name
FROM EMPLOEE WHERE EMP_NO = 1888;

,03257$17 <RXPXVWSURYLGHRQHKRVWYDULDEOHIRUHDFKFROXPQUHWXUQHGE\DTXHU\

ELIMINATING DUPLICATE COLUMNS WITH DISTINCT


,QDTXHU\UHWXUQLQJPXOWLSOHURZVLWPD\EHGHVLUDEOHWRHOLPLQDWHGXSOLFDWHFROXPQV)RU
H[DPSOHWKHIROORZLQJTXHU\PHDQWWRGHWHUPLQHLIWKH(03/2<((WDEOHFRQWDLQVHPSOR\HHV
ZLWKWKHODVWQDPH60,7+PLJKWORFDWHPDQ\VXFKURZV
EXEC SQL
DECLARE SMITH CURSOR FOR
SELECT LAST_NAME
FROM EMPLOYEE
WHERE LAST_NAME = "Smith";

7RHOLPLQDWHGXSOLFDWHFROXPQVLQVXFKDTXHU\XVHWKH',67,1&7NH\ZRUGZLWK6(/(&7)RU
H[DPSOHWKHIROORZLQJ6(/(&7\LHOGVRQO\DVLQJOHLQVWDQFHRI´6PLWKµ
EXEC SQL
DECLARE SMITH CURSOR FOR
SELECT DISTINCT LAST_NAME
FROM EMPLOYEE
WHERE LAST_NAME = "Smith";

',67,1&7DIIHFWVDOOFROXPQVOLVWHGLQD6(/(&7VWDWHPHQW

108 INTERBASE 5
UNDERSTANDING DATA RETRIEVAL WITH SELECT

4 5HWULHYLQJDJJUHJDWHFROXPQLQIRUPDWLRQ
6(/(&7FDQLQFOXGHDJJUHJDWHIXQFWLRQVIXQFWLRQVWKDWFDOFXODWHRUUHWULHYHDVLQJOHFROOHFWLYH
QXPHULFYDOXHIRUDFROXPQRUH[SUHVVLRQEDVHGRQHDFKTXDOLI\LQJURZLQDTXHU\UDWKHUWKDQ
UHWULHYLQJHDFKYDOXHVHSDUDWHO\7KHIROORZLQJWDEOHOLVWVWKHDJJUHJDWHIXQFWLRQVVXSSRUWHG
E\,QWHU%DVH

Function Purpose
AVG() Calculates the average numeric value for a set of values.
MIN() Retrieves the minimum value in a set of values.
MAX() Retrieves the maximum value in a set of values.
SUM() Calculates the total of numeric values in a set of values.
COUNT() Calculates the number of rows that satisfy the query’s search condition
(specified in the WHERE clause).
TABLE 6.11 Aggregate functions in SQL

)RUH[DPSOHWKHIROORZLQJTXHU\UHWXUQVWKHDYHUDJHVDODU\IRUDOOHPSOR\HHVLQWKH
(03/2<((WDEOH
EXEC SQL
SELECT AVG(SALARY)
INTO :avg_sal
FROM EMPLOYEE;

7KHIROORZLQJ6(/(&7UHWXUQVWKHQXPEHURITXDOLI\LQJURZVLWHQFRXQWHUVLQWKH
(03/2<((WDEOHERWKWKHPD[LPXPDQGPLQLPXPHPSOR\HHQXPEHURIHPSOR\HHVLQWKH
WDEOHDQGWKHWRWDOVDODU\RIDOOHPSOR\HHVLQWKHWDEOH
EXEC SQL
SELECT COUNT(*), MAX(EMP_NO), MIN(EMP_NO), SUM(SALARY)
INTO :counter, :maxno, :minno, :total_salary
FROM EMPLOYEE;

,IDILHOGYDOXHLQYROYHGLQDQDJJUHJDWHFDOFXODWLRQLV18//RUXQNQRZQWKHHQWLUHURZLV
DXWRPDWLFDOO\H[FOXGHGIURPWKHFDOFXODWLRQ$XWRPDWLFH[FOXVLRQSUHYHQWVDYHUDJHVIURP
EHLQJVNHZHGE\PHDQLQJOHVVGDWD
Note $JJUHJDWHIXQFWLRQVFDQDOVREHXVHGWRFDOFXODWHYDOXHVIRUJURXSVRIURZV7KH
UHVXOWLQJYDOXHLVFDOOHGDJURXSDJJUHJDWH)RUPRUHLQIRUPDWLRQDERXWXVLQJJURXSDJJUHJDWHV
VHH´*URXSLQJURZVZLWK*5283%<µRQSDJH 

PROGRAMMER’S GUIDE 109


CHAPTER 6 WORKING WITH DATA

4 0XOWLWDEOH6(/(&7VWDWHPHQWV
:KHQGDWDLVUHWULHYHGIURPPXOWLSOHWDEOHVYLHZVDQGVHOHFWSURFHGXUHVWKHVDPHFROXPQ
QDPHPD\DSSHDULQPRUHWKDQRQHWDEOH,QWKHVHFDVHVWKH6(/(&7VWDWHPHQWPXVWFRQWDLQ
HQRXJKLQIRUPDWLRQWRGLVWLQJXLVKOLNHQDPHGFROXPQVIURPRQHDQRWKHU
7RGLVWLQJXLVKFROXPQQDPHVLQPXOWLSOHWDEOHVSUHFHGHWKRVHFROXPQVZLWKRQHRIWKH
IROORZLQJTXDOLILHUVLQWKH6(/(&7FODXVH
g 7KHQDPHRIWKHWDEOHIROORZHGE\DSHULRG)RUH[DPSOH
(03/2<(((03B12LGHQWLILHVDFROXPQQDPHG(03B12LQWKH(03/2<((WDEOH
g $WDEOHFRUUHODWLRQQDPH DOLDV IROORZHGE\DSHULRG)RUH[DPSOHLIWKHFRUUHODWLRQQDPH
IRUWKH(03/2<((WDEOHLV(03WKHQ(03(03B12LGHQWLILHVDFROXPQQDPHG(03B12LQ
WKH(03/2<((6WDEOH
&RUUHODWLRQQDPHVFDQEHGHFODUHGIRUWDEOHVYLHZVDQGVHOHFWSURFHGXUHVLQWKH)520FODXVH
RIWKH6(/(&7VWDWHPHQW)RUPRUHLQIRUPDWLRQDERXWGHFODULQJFRUUHODWLRQQDPHVDQGIRU
H[DPSOHVRIWKHLUXVHVHH´'HFODULQJDQGXVLQJFRUUHODWLRQQDPHVµRQSDJH 

4 6SHFLI\LQJWUDQVDFWLRQQDPHV
,QWHU%DVHHQDEOHVDQ64/DSSOLFDWLRQWRUXQPDQ\VLPXOWDQHRXVWUDQVDFWLRQVLI
g (DFKWUDQVDFWLRQLVILUVWQDPHGZLWKD6(775$16$&7,21VWDWHPHQW
g (DFKGDWDPDQLSXODWLRQVWDWHPHQW 6(/(&7,16(5783'$7('(/(7( VSHFLILHVD
75$16$&7,21FODXVHWKDWLGHQWLILHVWKHQDPHRIWKHWUDQVDFWLRQXQGHUZKLFKLWRSHUDWHV
g 64/VWDWHPHQWVDUHQRWG\QDPLF
,Q6(/(&7WKH75$16$&7,21FODXVHLQWHUYHQHVEHWZHHQWKH6(/(&7NH\ZRUGDQGWKH
FROXPQOLVWDVLQWKHIROORZLQJV\QWD[IUDJPHQW
SELECT TRANSACTION name <col> [, <col> ...]

7KH75$16$&7,21FODXVHLVRSWLRQDOLQVLQJOHWUDQVDFWLRQSURJUDPVRULQSURJUDPVZKHUH
RQO\RQHWUDQVDFWLRQLVRSHQDWDWLPH,WPXVWEHXVHGLQDPXOWLWUDQVDFWLRQSURJUDP)RU
H[DPSOHWKHIROORZLQJ6(/(&7LVFRQWUROOHGE\WKHWUDQVDFWLRQ7
EXEC SQL
SELECT TRANSACTION T1:
COUNT(*), MAX(EMP_NO), MIN(EMP_NO), SUM(SALARY)
INTO :counter, :maxno, :minno, :total_salary
FROM EMPLOYEE;

)RUDFRPSOHWHGLVFXVVLRQRIWUDQVDFWLRQKDQGOLQJDQGQDPLQJVHH&KDSWHU´:RUNLQJZLWK
7UDQVDFWLRQVµ

110 INTERBASE 5
UNDERSTANDING DATA RETRIEVAL WITH SELECT

Specifying host variables with INTO


$VLQJOHWRQVHOHFWUHWXUQVGDWDWRDOLVWRIKRVWODQJXDJHYDULDEOHVVSHFLILHGE\DQ,172FODXVH
LQWKH6(/(&7VWDWHPHQW7KH,172FODXVHLPPHGLDWHO\IROORZVWKHOLVWRIWDEOHFROXPQV
IURPZKLFKGDWDLVWREHH[WUDFWHG(DFKKRVWYDULDEOHLQWKHOLVWPXVWEHSUHFHGHGE\DFRORQ
 DQGVHSDUDWHGIURPWKHQH[WE\DFRPPD
7KHKRVWODQJXDJHYDULDEOHVLQWKH,172FODXVHPXVWDOUHDG\KDYHEHHQGHFODUHGEHIRUHWKH\
FDQEHXVHG7KHQXPEHURUGHUDQGGDWDW\SHRIKRVWODQJXDJHYDULDEOHVPXVWFRUUHVSRQGWR
WKHQXPEHURUGHUDQGGDWDW\SHRIWKHFROXPQVUHWULHYHG2WKHUZLVHRYHUIORZRUGDWD
FRQYHUVLRQHUURUVPD\RFFXU
)RUH[DPSOHWKHIROORZLQJ&SURJUDPIUDJPHQWGHFODUHVWKUHHKRVWYDULDEOHVOQDPHIQDPH
DQGVDODU\7ZROQDPHDQGIQDPHDUHGHFODUHGDVFKDUDFWHUDUUD\VVDODU\LVGHFODUHGDVDORQJ
LQWHJHU7KH6(/(&7VWDWHPHQWVSHFLILHVWKDWWKUHHFROXPQVRIGDWDDUHWREHUHWULHYHGZKLOH
WKH,172FODXVHVSHFLILHVWKHKRVWYDULDEOHVLQWRZKLFKWKHGDWDVKRXOGEHUHDG
. . .
EXEC SQL
BEGIN DECLARE SECTION;
long salary;
char lname[20], fname[15];
EXEC SQL
END DECLARE SECTION;
. . .
EXEC SQL
SELECT LAST_NAME, FIRST_NAME, SALARY
INTO :lanem, :fname, :salary
FROM EMPLOYEE
WHERE LNAME = "Smith";
. . .
Note ,QDPXOWLURZVHOHFWWKH,172FODXVHLVSDUWRIWKH)(7&+VWDWHPHQWQRWWKH6(/(&7
VWDWHPHQW)RUPRUHLQIRUPDWLRQDERXWWKH,172FODXVHLQ)(7&+VHH´)HWFKLQJURZVZLWK
DFXUVRUµRQSDJH 

Listing tables to search with FROM


7KH)520FODXVHLVUHTXLUHGLQD6(/(&7VWDWHPHQW,WLGHQWLILHVWKHWDEOHVYLHZVRUVHOHFW
SURFHGXUHVIURPZKLFKGDWDLVWREHUHWULHYHG7KHFRPSOHWHV\QWD[RIWKH)520FODXVHLV
FROM table | view | procedure [alias] [, table | view | procedure [alias]
...]

PROGRAMMER’S GUIDE 111


CHAPTER 6 WORKING WITH DATA

7KHUHPXVWEHDWOHDVWRQHWDEOHYLHZRUVHOHFWSURFHGXUHQDPHIROORZLQJWKH)520
NH\ZRUG:KHQUHWULHYLQJGDWDIURPPXOWLSOHVRXUFHVHDFKVRXUFHPXVWEHOLVWHGDVVLJQHG
DQDOLDVDQGVHSDUDWHGIURPWKHQH[WZLWKDFRPPD)RUPRUHLQIRUPDWLRQDERXWVHOHFW
SURFHGXUHVVHH&KDSWHU´:RUNLQJZLWK6WRUHG 3URFHGXUHVµ

4 /LVWLQJDVLQJOHWDEOHRUYLHZ
7KH)520FODXVHLQWKHIROORZLQJ6(/(&7VSHFLILHVDVLQJOHWDEOH(03/2<((IURPZKLFK
WRUHWULHYHGDWD
EXEC SQL
SELECT LAST_NAME, FIRST_NAME, SALARY
INTO :lanem, :fname, :salary
FROM EMPLOYEE
WHERE LNAME = "Smith";

8VHWKHVDPH,172FODXVHV\QWD[WRVSHFLI\DYLHZRUVHOHFWSURFHGXUHDVWKHVRXUFHIRUGDWD
UHWULHYDOLQVWHDGRIDWDEOH)RUH[DPSOHWKHIROORZLQJ6(/(&7VSHFLILHVDVHOHFWSURFHGXUH
09,(:IURPZKLFKWRUHWULHYHGDWD09,(:UHWXUQVLQIRUPDWLRQIRUDOOPDQDJHUVZKRVHODVW
QDPHVEHJLQZLWKWKHOHWWHU´0µDQGWKH:+(5(FODXVHQDUURZVWKHURZVUHWXUQHGWRDVLQJOH
URZZKHUHWKH'(37B12FROXPQLV
EXEC SQL
SELECT DEPT_NO, LAST_NAME, FIRST_NAME, SALARY
INTO :lname, :fname, :salary
FROM MVIEW
WHERE DEPT_NO = 430;

)RUPRUHLQIRUPDWLRQDERXWVHOHFWSURFHGXUHVVHH&KDSWHU´:RUNLQJZLWK
6WRUHG 3URFHGXUHVµ

4 /LVWLQJPXOWLSOHWDEOHV
7RUHWULHYHGDWDIURPPXOWLSOHWDEOHVYLHZVRUVHOHFWSURFHGXUHVLQFOXGHDOOVRXUFHVLQWKH
)520FODXVHVHSDUDWLQJVRXUFHVIURPRQHDQRWKHUE\FRPPDV
7KHUHDUHWZRGLIIHUHQWSRVVLELOLWLHVWRFRQVLGHUZKHQZRUNLQJZLWKPXOWLSOHGDWDVRXUFHV
 7KHQDPHRIHDFKUHIHUHQFHGFROXPQLVXQLTXHDFURVVDOOWDEOHV
 7KHQDPHVRIRQHRUPRUHUHIHUHQFHGFROXPQVH[LVWLQWZRRUPRUHWDEOHV
,QWKHILUVWFDVHMXVWXVHWKHFROXPQQDPHVWKHPVHOYHVWRUHIHUHQFHWKHFROXPQV)RU
H[DPSOHWKHIROORZLQJTXHU\UHWXUQVGDWDIURPWZRWDEOHV'(3$570(17DQG(03/2<((
EXEC SQL
SELECT DEPARTMENT, DEPT_NO, LAST_NAME, FIRST_NAME, EMP_NO
INTO :dept_name, :dept_no, :lname, :fname, :empno

112 INTERBASE 5
UNDERSTANDING DATA RETRIEVAL WITH SELECT

FROM DEPARTMENT, EMPLOYEE


WHERE DEPT_NO = "Publications" AND MNGR_NO = EMP_NO;

,QWKHVHFRQGFDVHFROXPQQDPHVWKDWRFFXULQWZRRUPRUHWDEOHVPXVWEHGLVWLQJXLVKHG
IURPRQHDQRWKHUE\SUHFHGLQJHDFKFROXPQQDPHZLWKLWVWDEOHQDPHDQGDSHULRGLQWKH
6(/(&7FODXVH)RUH[DPSOHLIDQ(03B12FROXPQH[LVWVLQERWKWKH'(3$570(17DQG
(03/2<((WKHQWKHSUHYLRXVTXHU\PXVWEHUHFDVWDVIROORZV
EXEC SQL
SELECT DEPARTMENT, DEPT_NO, LAST_NAME, FIRST_NAME,
EMLOYEE.EMP_NO
INTO :dept_name, :dept_no, :lname, :fname, :empno
FROM DEPARTMENT, EMPLOYEE
WHERE DEPT_NO = "Publications" AND
DEPARTMENT.EMP_NO = EMPLOYEE.EMP_NO;

)RUPRUHLQIRUPDWLRQDERXWWKH6(/(&7FODXVHVHH´/LVWLQJFROXPQVWRUHWULHYHZLWK
6(/(&7µRQSDJH 

,03257$17 )RUTXHULHVLQYROYLQJMRLQVFROXPQQDPHVFDQEHTXDOLILHGE\FRUUHODWLRQQDPHVEULHI
DOWHUQDWHQDPHVRUDOLDVHVWKDWDUHDVVLJQHGWRHDFKWDEOHLQD)520FODXVHDQGVXEVWLWXWHG
IRUWKHPLQRWKHU6(/(&7VWDWHPHQWFODXVHVZKHQTXDOLI\LQJFROXPQQDPHV(YHQZKHQ
MRLQVDUHQRWLQYROYHGDVVLJQLQJDQGXVLQJFRUUHODWLRQQDPHVFDQUHGXFHWKHOHQJWKRI
FRPSOH[TXHULHV

4 'HFODULQJDQGXVLQJFRUUHODWLRQQDPHV
$FRUUHODWLRQQDPHRUDOLDVLVDWHPSRUDU\YDULDEOHWKDWUHSUHVHQWVDWDEOHQDPH,WFDQFRQWDLQ
XSWRDOSKDQXPHULFFKDUDFWHUVGROODUVLJQV  DQGXQGHUVFRUHV B EXWPXVWDOZD\VVWDUW
ZLWKDQDOSKDEHWLFFKDUDFWHU8VLQJEULHIFRUUHODWLRQQDPHVUHGXFHVW\SLQJRIORQJTXHULHV
&RUUHODWLRQQDPHVPXVWEHVXEVWLWXWHGIRUDFWXDOWDEOHQDPHVLQMRLQVDQGFDQEHVXEVWLWXWHG
IRUWKHPLQFRPSOH[TXHULHV
$FRUUHODWLRQQDPHLVDVVRFLDWHGZLWKDWDEOHLQWKH)520FODXVHLWUHSODFHVWDEOHQDPHVWR
TXDOLI\FROXPQQDPHVHYHU\ZKHUHHOVHLQWKHVWDWHPHQW)RUH[DPSOHWRDVVRFLDWHWKH
FRUUHODWLRQQDPH'(37ZLWKWKH'(3$570(17WDEOHDQG(03ZLWKWKH(03/2<((6WDEOH
D)520FODXVHPLJKWDSSHDUDV
FROM DEPARTMENT DEPT, EMPLOYEE EMP

/LNHDQDFWXDOWDEOHQDPHDFRUUHODWLRQQDPHLVXVHGWRTXDOLI\FROXPQQDPHVZKHUHYHUWKH\
DSSHDULQD6(/(&7VWDWHPHQW)RUH[DPSOHWKHIROORZLQJTXHU\HPSOR\VWKHFRUUHODWLRQ
QDPHV'(37DQG(03SUHYLRXVO\GHVFULEHG
EXEC SQL
SELECT DEPARTMENT, DEPT_NO, LAST_NAME, FIRST_NAME,
EMLOYEE.EMP_NO

PROGRAMMER’S GUIDE 113


CHAPTER 6 WORKING WITH DATA

INTO :dept_name, :dept_no, :lname, :fname, :empno


FROM DEPARTMENT DEPT, EMPLOYEE EMP
WHERE DEPT_NO = "Publications" AND DEPT.EMP_NO = EMP.EMP_NO;

)RUPRUHLQIRUPDWLRQDERXWWKH6(/(&7FODXVHVHH´/LVWLQJFROXPQVWRUHWULHYHZLWK
6(/(&7µRQSDJH 

Restricting row retrieval with WHERE


,QDTXHU\WKH:+(5(FODXVHVSHFLILHVWKHGDWDDURZPXVW RUPXVWQRW FRQWDLQWREH
UHWULHYHG
,QVLQJOHWRQVHOHFWVZKHUHDTXHU\PXVWRQO\UHWXUQRQHURZ:+(5(LVPDQGDWRU\XQOHVVD
VHOHFWSURFHGXUHVSHFLILHGLQWKH)520FODXVHUHWXUQVRQO\RQHURZLWVHOI
,Q6(/(&7VWDWHPHQWVZLWKLQ'(&/$5(&85625VWDWHPHQWVWKH:+(5(FODXVHLVRSWLRQDO
,IWKH:+(5(FODXVHLVRPLWWHGDTXHU\UHWXUQVDOOURZVLQWKHWDEOH7RUHWULHYHDVXEVHWRI
URZVLQDWDEOHDFXUVRUGHFODUDWLRQPXVWLQFOXGHD:+(5(FODXVH
7KHVLPSOHV\QWD[IRU:+(5(LV
WHERE <search_condition>

)RUH[DPSOHWKHIROORZLQJVLPSOH:+(5(FODXVHWHVWVDURZWRVHHLIWKH
'(3$570(17FROXPQLV´3XEOLFDWLRQVµ
WHERE DEPARTMENT = "Publications"

4 :KDWLVDVHDUFKFRQGLWLRQ"
%HFDXVHWKH:+(5(FODXVHVSHFLILHVWKHW\SHRIGDWDDTXHU\LVVHDUFKLQJIRULWLVRIWHQFDOOHG
DVHDUFKFRQGLWLRQ$TXHU\H[DPLQHVHDFKURZLQDWDEOHWRVHHLILWPHHWVWKHFULWHULDVSHFLILHG
LQWKHVHDUFKFRQGLWLRQ,ILWGRHVWKHURZTXDOLILHVIRUUHWULHYDO
:KHQDURZLVFRPSDUHGWRDVHDUFKFRQGLWLRQRQHRIWKUHHYDOXHVLVUHWXUQHG
g 7UXH$URZPHHWVWKHFRQGLWLRQVVSHFLILHGLQWKH:+(5(FODXVH
g )DOVH$URZIDLOVWRPHHWWKHFRQGLWLRQVVSHFLILHGLQWKH:+(5(FODXVH
g 8QNQRZQ$FROXPQWHVWHGLQWKH:+(5(FODXVHFRQWDLQVDQXQNQRZQYDOXHWKDWFRXOGQRW
EHHYDOXDWHGEHFDXVHRID18//FRPSDULVRQ
0RVWVHDUFKFRQGLWLRQVQRPDWWHUKRZFRPSOH[HYDOXDWHWR7UXHRU)DOVH$QH[SUHVVLRQ
WKDWHYDOXDWHVWR7UXHRU)DOVH³OLNHWKHVHDUFKFRQGLWLRQLQWKH:+(5(FODXVH³LVFDOOHGD
%RROHDQH[SUHVVLRQ

114 INTERBASE 5
UNDERSTANDING DATA RETRIEVAL WITH SELECT

4 6WUXFWXUHRIDVHDUFKFRQGLWLRQ
$W\SLFDOVLPSOHVHDUFKFRQGLWLRQFRPSDUHVDYDOXHLQRQHFROXPQDJDLQVWDFRQVWDQWRUD
YDOXHLQDQRWKHUFROXPQ)RUH[DPSOHWKHIROORZLQJ:+(5(FODXVHWHVWVDURZWRVHHLID
ILHOGHTXDOVDKDUGFRGHGFRQVWDQW
WHERE DEPARTMENT = "Publications"

7KLVVHDUFKFRQGLWLRQKDVWKUHHHOHPHQWVDFROXPQQDPHDFRPSDULVRQRSHUDWRU WKHHTXDO
VLJQ DQGDFRQVWDQW0RVWVHDUFKFRQGLWLRQVDUHPRUHFRPSOH[WKDQWKLV7KH\LQYROYH
DGGLWLRQDOHOHPHQWVDQGFRPELQDWLRQVRIVLPSOHVHDUFKFRQGLWLRQV7KHIROORZLQJWDEOH
GHVFULEHVH[SUHVVLRQHOHPHQWVWKDWFDQEHXVHGLQVHDUFKFRQGLWLRQV

Element Description
Column names Columns from tables listed in the FROM clause, against which to search or
compare values.
Host-language variables Program variables containing changeable values. When used in a SELECT,
host-language variables must be preceded by a colon (:).
Constants Hard-coded numbers or quoted strings, like 507 or “Tokyo”.
Concatenation operators ||, used to combine character strings.
Arithmetic operators +, –, *, and /, used to calculate and evaluate search condition values.
Logical operators Keywords, NOT, AND, and OR, used within simple search conditions, or to
combine simple search conditions to make complex searches. A logical
operation evaluates to true or false.
TABLE 6.12 Elements of WHERE clause SEARCH conditions

PROGRAMMER’S GUIDE 115


CHAPTER 6 WORKING WITH DATA

Element Description
Comparison operators <, >, <=, >=, =, and <>, used to compare a value on the left side of the
operator to another on the right. A comparative operation evaluates to True
or False.
Other, more specialized comparison operators include ALL, ANY, BETWEEN,
CONTAINING, EXISTS, IN, IS, LIKE, NULL, SINGULAR, SOME, and STARTING WITH. These
operators can evaluate to True, False, or Unknown.
COLLATE clause Comparisons of CHAR and VARCHAR values can sometimes take advantage of a
COLLATE clause to force the way text values are compared.

Stored procedures Reusable SQL statement blocks that can receive and return parameters, and
that are stored as part of a database’s metadata. For more information about
stored procedures in queries, see Chapter 11, “Working with
Stored Procedures.”
Subqueries A SELECT statement nested within the WHERE clause to return or calculate
values against which rows searched by the main SELECT statement are
compared. For more information about subqueries, see “Using subqueries”
on page 140.
Parentheses Group related parts of search conditions which should be processed
separately to produce a single value which is then used to evaluate the search
condition. Parenthetical expressions can be nested.
TABLE 6.12 Elements of WHERE clause SEARCH conditions (continued)

&RPSOH[VHDUFKFRQGLWLRQVFDQEHFRQVWUXFWHGE\FRPELQLQJVLPSOHVHDUFKFRQGLWLRQVLQ
GLIIHUHQWZD\V)RUH[DPSOHWKHIROORZLQJ:+(5(FODXVHXVHVDFROXPQQDPHWKUHH
FRQVWDQWVWKUHHFRPSDULVRQRSHUDWRUVDQGDVHWRIJURXSLQJSDUHQWKHVHVWRUHWULHYHRQO\
WKRVHURZVIRUHPSOR\HHVZLWKVDODULHVEHWZHHQDQG
WHERE DEPARTMENT = "Publications" AND
(SALARY > 60000 AND SALARY < 120000)

6HDUFKFRQGLWLRQVLQ:+(5(FODXVHVRIWHQFRQWDLQQHVWHG6(/(&7VWDWHPHQWVRUVXETXHULHV
)RUH[DPSOHLQWKHIROORZLQJTXHU\WKH:+(5(FODXVHFRQWDLQVDVXETXHU\WKDWXVHVWKH
DJJUHJDWHIXQFWLRQ$9* WRUHWULHYHDOLVWRIDOOGHSDUWPHQWVZLWKELJJHUWKDQDYHUDJH
VDODULHV
EXEC SQL
DECLARE WELL_PAID CURSOR FOR
SELECT DEPT_NO
INTO :wellpaid
FROM DEPARTMENT
WHERE SALARY > (SELECT AVG(SALARY) FROM DEPARTMENT);

116 INTERBASE 5
UNDERSTANDING DATA RETRIEVAL WITH SELECT

)RUDJHQHUDOGLVFXVVLRQRIEXLOGLQJVHDUFKFRQGLWLRQVIURP64/H[SUHVVLRQVVHH
´8QGHUVWDQGLQJ64/H[SUHVVLRQVµRQSDJH )RUPRUHLQIRUPDWLRQDERXWXVLQJ
VXETXHULHVWRVSHFLI\VHDUFKFRQGLWLRQVVHH´8VLQJVXETXHULHVµRQSDJH )RUPRUH
LQIRUPDWLRQDERXWDJJUHJDWHIXQFWLRQVVHH´5HWULHYLQJDJJUHJDWHFROXPQLQIRUPDWLRQµRQ
SDJH 

4 &ROODWLRQRUGHULQFRPSDULVRQV
:KHQ&+$5RU9$5&+$5YDOXHVDUHFRPSDUHGLQD:+(5(FODXVHLWFDQEHQHFHVVDU\WR
VSHFLI\DFROODWLRQRUGHUIRUWKHFRPSDULVRQVLIWKHYDOXHVEHLQJFRPSDUHGXVHGLIIHUHQW
FROODWLRQRUGHUV
7RVSHFLI\WKHFROODWLRQRUGHUWRXVHIRUDYDOXHGXULQJDFRPSDULVRQLQFOXGHD&2//$7(
FODXVHDIWHUWKHYDOXH)RUH[DPSOHLQWKHIROORZLQJ:+(5(FODXVHIUDJPHQWIURPDQ
HPEHGGHGDSSOLFDWLRQWKHYDOXHWRWKHOHIWRIWKHFRPSDULVRQRSHUDWRULVIRUFHGWREH
FRPSDUHGXVLQJDVSHFLILFFROODWLRQ
WHERE LNAME COLLATE FR_CA = :lname_search;

)RUPRUHLQIRUPDWLRQDERXWFROODWLRQRUGHUDQGDOLVWRIFROODWLRQVDYDLODEOHWR,QWHU%DVHVHH
WKH'DWD'HILQLWLRQ*XLGH

Sorting rows with ORDER BY


%\GHIDXOWDTXHU\UHWULHYHVURZVLQWKHH[DFWRUGHULWILQGVWKHPLQDWDEOHDQGEHFDXVH
LQWHUQDOWDEOHVWRUDJHLVXQRUGHUHGUHWULHYDOWRRLVOLNHO\WREHXQRUGHUHG7RVSHFLI\WKH
RUGHULQZKLFKURZVDUHUHWXUQHGE\DTXHU\XVHWKHRSWLRQDO25'(5%<FODXVHDWWKHHQGRI
D6(/(&7VWDWHPHQW
25'(5%<UHWULHYHVURZVEDVHGRQDFROXPQOLVW(YHU\FROXPQLQWKH25'(5%<FODXVH
PXVWDOVRDSSHDUVRPHZKHUHLQWKH6(/(&7FODXVHDWWKHVWDUWRIWKHVWDWHPHQW(DFKFROXPQ
FDQRSWLRQDOO\EHRUGHUHGLQDVFHQGLQJRUGHU $6&WKHGHIDXOW RUGHVFHQGLQJRUGHU '(6& 
7KHFRPSOHWHV\QWD[RI25'(5%<LV
ORDER BY col [COLLATE collation] [ASC | DESC]
[,col [COLLATE collation] [ASC | DESC] ...];

)RUH[DPSOHWKHIROORZLQJFXUVRUGHFODUDWLRQRUGHUVRXWSXWEDVHGRQWKH/$67B1$0(
FROXPQ%HFDXVH'(6&LVVSHFLILHGLQWKH25'(5%<FODXVHHPSOR\HHVDUHUHWULHYHGIURP=
WR$
EXEC SQL
DECLARE PHONE_LIST CURSOR FOR
SELECT LAST_NAME, FIRST_NAME, PHONE_EXT
FROM EMPLOYEE

PROGRAMMER’S GUIDE 117


CHAPTER 6 WORKING WITH DATA

WHERE PHONE_EXT IS NOT NULL


ORDER BY LAST_NAME DESC, FIRST_NAME;

4 25'(5%<ZLWKPXOWLSOHFROXPQV
,IPRUHWKDQRQHFROXPQLVVSHFLILHGLQDQ25'(5%<FODXVHURZVDUHILUVWDUUDQJHGE\WKH
YDOXHVLQWKHILUVWFROXPQ7KHQURZVWKDWFRQWDLQWKHVDPHILUVWFROXPQYDOXHDUHDUUDQJHG
DFFRUGLQJWRWKHYDOXHVLQWKHVHFRQGFROXPQDQGVRRQ(DFK25'(5%<FROXPQFDQ
LQFOXGHLWVRZQVRUWRUGHUVSHFLILFDWLRQ

,03257$17 ,QPXOWLFROXPQVRUWVDIWHUDVRUWRUGHULVVSHFLILHGLWDSSOLHVWRDOOVXEVHTXHQWFROXPQV
XQWLODQRWKHUVRUWRUGHULVVSHFLILHGDVLQWKHSUHYLRXVH[DPSOH7KLVDWWULEXWHLVVRPHWLPHV
FDOOHGVWLFN\VRUWRUGHU)RUH[DPSOHWKHIROORZLQJFXUVRUGHFODUDWLRQRUGHUVUHWULHYDOE\
/$67B1$0(LQGHVFHQGLQJRUGHUWKHQUHILQHVLWDOSKDEHWLFDOO\ZLWKLQ/$67B1$0(JURXSV
E\),567B1$0(LQDVFHQGLQJRUGHU
EXEC SQL
DECLARE PHONE_LIST CURSOR FOR
SELECT LAST_NAME, FIRST_NAME, PHONE_EXT
FROM EMPLOYEE
WHERE PHONE_EXT IS NOT NULL
ORDER BY LAST_NAME DESC, FIRST_NAME ASC;

4 &ROODWLRQRUGHULQDQ25'(5%<FODXVH
:KHQ&+$5RU9$5&+$5FROXPQVDUHRUGHUHGLQD6(/(&7VWDWHPHQWLWFDQEHQHFHVVDU\
WRVSHFLI\DFROODWLRQRUGHUIRUWKHRUGHULQJHVSHFLDOO\LIFROXPQVXVHGIRURUGHULQJXVH
GLIIHUHQWFROODWLRQRUGHUV
7RVSHFLI\WKHFROODWLRQRUGHUWRXVHIRURUGHULQJDFROXPQLQWKH25'(5%<FODXVHLQFOXGH
D&2//$7(FODXVHDIWHUWKHFROXPQQDPH)RUH[DPSOHLQWKHIROORZLQJ25'(5%<FODXVH
DGLIIHUHQWFROODWLRQRUGHUIRUHDFKRIWZRFROXPQVLVVSHFLILHG
. . .
ORDER BY LNAME COLLATE FR_CA, FNAME COLLATE FR_FR;

)RUPRUHLQIRUPDWLRQDERXWFROODWLRQRUGHUDQGDOLVWRIDYDLODEOHFROODWLRQVLQ,QWHU%DVHVHH
WKH'DWD'HILQLWLRQ*XLGH

118 INTERBASE 5
UNDERSTANDING DATA RETRIEVAL WITH SELECT

Grouping rows with GROUP BY


7KHRSWLRQDO*5283%<FODXVHHQDEOHVDTXHU\WRUHWXUQVXPPDU\LQIRUPDWLRQDERXWJURXSV
RIURZVWKDWVKDUHFROXPQYDOXHVLQVWHDGRIUHWXUQLQJHDFKTXDOLI\LQJURZ7KHFRPSOHWH
V\QWD[RI*5283%<LV
GROUP BY col [COLLATE collation] [, col [COLLATE collation] ...]

)RUH[DPSOHFRQVLGHUWZRFXUVRUGHFODUDWLRQV7KHILUVWGHFODUDWLRQUHWXUQVWKHQDPHVRIDOO
HPSOR\HHVHDFKGHSDUWPHQWDQGDUUDQJHVUHWULHYDOLQDVFHQGLQJDOSKDEHWLFRUGHUE\
GHSDUWPHQWDQGHPSOR\HHQDPH
EXEC SQL
DECLARE DEPT_EMP CURSOR FOR
SELECT DEPARTMENT, LAST_NAME, FIRST_NAME
FROM DEPARTMENT D, EMPLOYEE E
WHERE D.DEPT_NO = E.DEPT_NO"
ORDER BY DEPARTMENT, LAST_NAME, FIRST_NAME;

,QFRQWUDVWWKHQH[WFXUVRULOOXVWUDWHVWKHXVHRIDJJUHJDWHIXQFWLRQVZLWK*5283%<WR
UHWXUQUHVXOWVNQRZQDVJURXSDJJUHJDWHV,WUHWXUQVWKHDYHUDJHVDODU\RIDOOHPSOR\HHVLQHDFK
GHSDUWPHQW7KH*5283%<FODXVHDVVXUHVWKDWDYHUDJHVDODULHVDUHFDOFXODWHGDQGUHWULHYHG
EDVHGRQGHSDUWPHQWQDPHVZKLOHWKH25'(5%<FODXVHDUUDQJHVUHWULHYHGURZV
DOSKDEHWLFDOO\E\GHSDUWPHQWQDPH
EXEC SQL
DECLARE AVG_DEPT_SAL CURSOR FOR
SELECT DEPARTMENT, AVG(SALARY)
FROM DEPARTMENT D, EMPLOYEE E
WHERE D.DEPT_NO = E.DEPT_NO
GROUP BY DEPARTMENT
ORDER BY DEPARTMENT;

4 &ROODWLRQRUGHULQD*5283%<FODXVH
:KHQ&+$5RU9$5&+$5FROXPQVDUHJURXSHGLQD6(/(&7VWDWHPHQWLWFDQEHQHFHVVDU\
WRVSHFLI\DFROODWLRQRUGHUIRUWKHJURXSLQJHVSHFLDOO\LIFROXPQVXVHGIRUJURXSLQJXVH
GLIIHUHQWFROODWLRQRUGHUV
7RVSHFLI\WKHFROODWLRQRUGHUWRXVHIRUJURXSLQJFROXPQVLQWKH*5283%<FODXVHLQFOXGH
D&2//$7(FODXVHDIWHUWKHFROXPQQDPH)RUH[DPSOHLQWKHIROORZLQJ*5283%<FODXVH
WKHFROODWLRQRUGHUIRUWZRFROXPQVLVVSHFLILHG
. . .
GROUP BY LNAME COLLATE FR_CA, FNAME COLLATE FR_CA;

PROGRAMMER’S GUIDE 119


CHAPTER 6 WORKING WITH DATA

)RUPRUHLQIRUPDWLRQDERXWFROODWLRQRUGHUDQGDOLVWRIFROODWLRQRUGHUVDYDLODEOHLQ
,QWHU%DVHVHHWKH'DWD'HILQLWLRQ*XLGH

4 /LPLWDWLRQVRI*5283%<
:KHQXVLQJ*5283%<EHDZDUHRIWKHIROORZLQJOLPLWDWLRQV
g (DFKFROXPQQDPHWKDWDSSHDUVLQD*5283%<FODXVHPXVWDOVREHVSHFLILHGLQWKH6(/(&7
FODXVH
g *5283%<FDQQRWVSHFLI\DFROXPQZKRVHYDOXHVDUHGHULYHGIURPDPDWKHPDWLFDO
DJJUHJDWHRUXVHUGHILQHGIXQFWLRQ
g *5283%<FDQQRWEHXVHGLQ6(/(&7VWDWHPHQWVWKDW
à &RQWDLQDQ,172FODXVH VLQJOHWRQVHOHFWV 
à 8VHDVXETXHU\ZLWKD)520FODXVHZKLFKUHIHUHQFHVDYLHZZKRVHGHILQLWLRQFRQWDLQVD
*5283%<RU+$9,1*FODXVH
g )RUHDFK6(/(&7FODXVHLQDTXHU\LQFOXGLQJVXETXHULHVWKHUHFDQRQO\EHRQH*5283%<
FODXVH

Restricting grouped rows with HAVING


-XVWDVD:+(5(FODXVHUHGXFHVWKHQXPEHURIURZVUHWXUQHGE\D6(/(&7FODXVHWKH
+$9,1*FODXVHFDQEHXVHGWRUHGXFHWKHQXPEHURIURZVUHWXUQHGE\D*5283%<FODXVH
7KHV\QWD[RI+$9,1*LV
HAVING <search_condition>

+$9,1*XVHVVHDUFKFRQGLWLRQVWKDWDUHOLNHWKHVHDUFKFRQGLWLRQVWKDWFDQDSSHDULQWKH
:+(5(FODXVHEXWZLWKWKHIROORZLQJUHVWULFWLRQV
g (DFKVHDUFKFRQGLWLRQXVXDOO\FRUUHVSRQGVWRDQDJJUHJDWHIXQFWLRQXVHGLQWKH6(/(&7
FODXVH
g 7KH)520FODXVHRIDVXETXHU\DSSHDULQJLQD+$9,1*FODXVHFDQQRWQDPHDQ\WDEOHRUYLHZ
VSHFLILHGLQWKHPDLQTXHU\·V)520FODXVH
g $FRUUHODWHGVXETXHU\FDQQRWEHXVHGLQD+$9,1*FODXVH
)RUH[DPSOHWKHIROORZLQJFXUVRUGHFODUDWLRQUHWXUQVWKHDYHUDJHVDODU\IRUDOOHPSOR\HHVLQ
HDFKGHSDUWPHQW7KH*5283%<FODXVHDVVXUHVWKDWDYHUDJHVDODULHVDUHFDOFXODWHGDQG
UHWULHYHGEDVHGRQGHSDUWPHQWQDPHV7KH+$9,1*FODXVHUHVWULFWVUHWULHYDOWRWKRVHJURXSV
ZKHUHWKHDYHUDJHVDODU\LVJUHDWHUWKDQZKLOHWKH25'(5%<FODXVHDUUDQJHVUHWULHYHG
URZVDOSKDEHWLFDOO\E\GHSDUWPHQWQDPH
EXEC SQL

120 INTERBASE 5
UNDERSTANDING DATA RETRIEVAL WITH SELECT

DECLARE SIXTY_THOU CURSOR FOR


SELECT DEPARTMENT, AVG(SALARY)
FROM DEPARTMENT D, EMPLOYEE E
WHERE D.DEPT_NO = E.DEPT_NO
GROUP BY DEPARTMENT
HAVING AVG(SALARY) > 60000
ORDER BY DEPARTMENT;
Note +$9,1*FDQDOVREHXVHGZLWKRXW*5283%<,QWKLVFDVHDOOURZVUHWULHYHGE\D
6(/(&7DUHWUHDWHGDVDVLQJOHJURXSDQGHDFKFROXPQQDPHGLQWKH6(/(&7FODXVHLV
QRUPDOO\RSHUDWHGRQE\DQDJJUHJDWHIXQFWLRQ
)RUPRUHLQIRUPDWLRQDERXWVHDUFKFRQGLWLRQVVHH´5HVWULFWLQJURZUHWULHYDOZLWK:+(5(µ
RQSDJH )RUPRUHLQIRUPDWLRQDERXWVXETXHULHVVHH´8VLQJVXETXHULHVµRQSDJH 

Appending tables with UNION


6RPHWLPHVWZRRUPRUHWDEOHVLQDGDWDEDVHDUHLGHQWLFDOO\VWUXFWXUHGRUKDYHFROXPQVWKDW
FRQWDLQVLPLODUGDWD:KHUHWDEOHVWUXFWXUHVRYHUODSLQIRUPDWLRQIURPWKRVHWDEOHVFDQEH
FRPELQHGWRSURGXFHDVLQJOHUHVXOWVWDEOHWKDWUHWXUQVDSURMHFWLRQIRUHYHU\TXDOLI\LQJURZ
LQERWKWDEOHV7KH81,21FODXVHUHWULHYHVDOOURZVIURPHDFKWDEOHDSSHQGVRQHWDEOHWRWKH
HQGRIDQRWKHUDQGHOLPLQDWHVGXSOLFDWHURZV
8QLRQVDUHFRPPRQO\XVHGWRSHUIRUPDJJUHJDWHRSHUDWLRQVRQWDEOHV
7KHV\QWD[IRU81,21LV
UNION SELECT col [, col ...] | * FROM <tableref> [, <tableref> ...]

)RUH[DPSOHWKUHHWDEOHV&,7,(6&28175,(6DQG1$7,21$/B3$5.6HDFKFRQWDLQWKH
QDPHVRIFLWLHV$VVXPLQJWULJJHUVKDYHQRWEHHQFUHDWHGWKDWHQVXUHWKDWDFLW\HQWHUHGLQ
RQHWDEOHLVDOVRHQWHUHGLQWKHRWKHUVWRZKLFKLWDOVRDSSOLHV81,21FDQEHXVHGWRUHWULHYH
WKHQDPHVRIDOOFLWLHVWKDWDSSHDULQDQ\RIWKHVHWDEOHV
EXEC SQL
DECLARE ALLCITIES CURSOR FOR
SELECT CIT.CITY FROM CITIES CIT
UNION SELECT COU.CAPITAL FROM COUNTRIES COU
UNION SELECT N.PARKCITY FROM NATIONAL_PARKS N;

7,3 ,IWZRRUPRUHWDEOHVVKDUHHQWLUHO\LGHQWLFDOVWUXFWXUHV³VLPLODUO\QDPHGFROXPQVLGHQWLFDO
GDWDW\SHVDQGVLPLODUGDWDYDOXHVLQHDFKFROXPQ³81,21FDQUHWXUQDOOURZVIRUHDFKWDEOH
E\VXEVWLWXWLQJDQDVWHULVN IRUVSHFLILFFROXPQQDPHVLQWKH6(/(&7FODXVHVRIWKH
81,21

PROGRAMMER’S GUIDE 121


CHAPTER 6 WORKING WITH DATA

Specifying a query plan with PLAN


7RSURFHVVD6(/(&7VWDWHPHQW,QWHU%DVHXVHVDQLQWHUQDODOJRULWKPFDOOHGWKHTXHU\
RSWLPL]HUWRGHWHUPLQHWKHPRVWHIILFLHQWSODQIRUUHWULHYLQJGDWD7KHPRVWHIILFLHQWUHWULHYDO
SODQDOVRUHVXOWVLQWKHIDVWHVWUHWULHYDOWLPH2FFDVLRQDOO\WKHRSWLPL]HUPD\FKRRVHDSODQ
WKDWLVOHVVHIILFLHQW)RUH[DPSOHZKHQWKHQXPEHURIURZVLQDWDEOHJURZVVXIILFLHQWO\ODUJH
RUZKHQPDQ\GXSOLFDWHURZVDUHLQVHUWHGRUGHOHWHGIURPLQGH[HGFROXPQVLQDWDEOHEXW
WKHLQGH[·VVHOHFWLYLW\LVQRWUHFRPSXWHGWKHRSWLPL]HUPLJKWFKRRVHDOHVVHIILFLHQWSODQ
)RUWKHVHRFFDVLRQV6(/(&7SURYLGHGDQRSWLRQDO3/$1FODXVHWKDWHQDEOHVDNQRZOHGJHDEOH
SURJUDPPHUWRVSHFLI\DUHWULHYDOSODQ$TXHU\SODQLVEXLOWDURXQGWKHDYDLODELOLW\RILQGH[HV
WKHZD\LQGH[HVDUHMRLQHGRUPHUJHGDQGDFKRVHQDFFHVVPHWKRG
7RVSHFLI\DTXHU\SODQXVHWKHIROORZLQJ3/$1V\QWD[
PLAN <plan_expr>
<plan_expr> =
[JOIN | [SORT] MERGE] (<plan_item> | <plan_expr>
[, <plan_item> | <plan_expr> ...])
<plan_item> = {table | alias}
NATURAL | INDEX ( <index> [, <index> ...]) | ORDER <index>

7KH3/$1V\QWD[HQDEOHVVSHFLI\LQJDVLQJOHWDEOHRUDMRLQRIWZRRUPRUHWDEOHVLQDVLQJOH
SDVV3ODQH[SUHVVLRQVFDQEHQHVWHGLQSDUHQWKHVHVWRVSHFLI\DQ\FRPELQDWLRQRIMRLQV
'XULQJUHWULHYDOLQIRUPDWLRQIURPGLIIHUHQWWDEOHVLVMRLQHGWRVSHHGUHWULHYDO,ILQGH[HVDUH
GHILQHGIRUWKHLQIRUPDWLRQWREHMRLQHGWKHQWKHVHLQGH[HVDUHXVHGWRSHUIRUPDMRLQ7KH
RSWLRQDO-2,1NH\ZRUGFDQEHXVHGWRGRFXPHQWWKLVW\SHRIRSHUDWLRQ:KHQQRLQGH[HV
H[LVWIRUWKHLQIRUPDWLRQWRMRLQUHWULHYDOVSHHGFDQEHLPSURYHGE\VSHFLI\LQJ62570(5*(
LQVWHDGRI-2,1
$SODQBLWHP!LVWKHQDPHRIDWDEOHWRVHDUFKIRUGDWD,IDWDEOHLVXVHGPRUHWKDQRQFHLQ
DTXHU\DOLDVHVPXVWEHXVHGWRGLVWLQJXLVKWKHPLQWKH3/$1FODXVH3DUWRIWKHSODQBLWHP!
VSHFLILFDWLRQLQGLFDWHVWKHZD\WKDWURZVVKRXOGEHDFFHVVHG7KHIROORZLQJFKRLFHVDUH
SRVVLEOH
g 1$785$/WKHGHIDXOWRUGHUVSHFLILHVWKDWURZVDUHDFFHVVHGVHTXHQWLDOO\LQQRGHILQHGRUGHU
)RUXQLQGH[HGLWHPVWKLVLVWKHRQO\RSWLRQ
g ,1'(;VSHFLILHVWKDWRQHRUPRUHLQGH[HVVKRXOGEHXVHGWRDFFHVVLWHPV$OOLQGH[HVWREH
XVHGPXVWEHVSHFLILHG,IDQ\%RROHDQRUMRLQWHUPVUHPDLQDIWHUDOOLQGH[HVDUHXVHGWKH\
ZLOOEHHYDOXDWHGZLWKRXWEHQHILWRIDQLQGH[,IDQ\LQGH[HVDUHVSHFLILHGWKDWFDQQRWEHXVHG
DQHUURULVUHWXUQHG
g 25'(5VSHFLILHVWKDWLWHPVDUHWREHVRUWHGEDVHGRQDVSHFLILHGLQGH[

122 INTERBASE 5
SELECTING A SINGLE ROW

Selecting a single row


$QRSHUDWLRQWKDWUHWULHYHVDVLQJOHURZRIGDWDLVFDOOHGDVLQJOHWRQVHOHFW7RUHWULHYHDVLQJOH
URZIURPDWDEOHWRUHWULHYHDFROXPQGHILQHGZLWKDXQLTXHLQGH[RUWRVHOHFWDQDJJUHJDWH
YDOXHOLNH&2817 RU$9* IURPDWDEOHXVHWKHIROORZLQJ6(/(&7VWDWHPHQWV\QWD[
SELECT <col> [, <col> ...]
INTO :variable [, :variable ...]
FROM table
WHERE <search_condition>;

7KHPDQGDWRU\,172FODXVHVSHFLILHVWKHKRVWYDULDEOHVZKHUHUHWULHYHGGDWDLVFRSLHGIRUXVH
LQWKHSURJUDP(DFKKRVWYDULDEOH·VQDPHPXVWEHSUHFHGHGE\DFRORQ  )RUHDFKFROXPQ
UHWULHYHGWKHUHPXVWEHRQHKRVWYDULDEOHRIDFRUUHVSRQGLQJGDWDW\SH&ROXPQVDUHUHWULHYHG
LQWKHRUGHUWKH\DUHOLVWHGLQWKH6(/(&7FODXVHDQGDUHFRSLHGLQWRKRVWYDULDEOHVLQWKH
RUGHUWKHYDULDEOHVDUHOLVWHGLQWKH,172FODXVH
7KH:+(5(FODXVHPXVWVSHFLI\DVHDUFKFRQGLWLRQWKDWJXDUDQWHHVWKDWRQO\RQHURZLV
UHWULHYHG,IWKH:+(5(FODXVHGRHVQRWUHGXFHWKHQXPEHURIURZVUHWXUQHGWRDVLQJOHURZ
WKH6(/(&7IDLOV

,03257$17 7RVHOHFWGDWDIURPDWDEOHDXVHUPXVWKDYH6(/(&7SULYLOHJHIRUDWDEOHRUDVWRUHG
SURFHGXUHLQYRNHGE\WKHXVHU·VDSSOLFDWLRQPXVWKDYH6(/(&7SULYLOHJHVIRUWKHWDEOH
)RUH[DPSOHWKHIROORZLQJ6(/(&7UHWULHYHVLQIRUPDWLRQIURPWKH
'(3$570(17WDEOHIRUWKHGHSDUWPHQW3XEOLFDWLRQV
EXEC SQL
SELECT DEPARTMENT, DEPT_NO, HEAD_DEPT, BUDGET, LOCATION, PHONE_NO
INTO :deptname, :dept_no, :manager, :budget, :location, :phone
FROM DEPARTMENT
WHERE DEPARTMENT = "Publications";

:KHQ64/UHWULHYHVWKHVSHFLILHGURZLWFRSLHVWKHYDOXHLQ'(3$570(17WRWKHKRVW
YDULDEOHGHSWQDPHFRSLHVWKHYDOXHLQ'(37B12WR GHSWBQRFRSLHVWKHYDOXHLQ+($'B'(37
WRPDQDJHUDQGVRRQ

Selecting multiple rows


0RVWTXHULHVVSHFLI\VHDUFKFRQGLWLRQVWKDWUHWULHYHPRUHWKDQRQHURZ)RUH[DPSOHDTXHU\
WKDWDVNVWRVHHDOOHPSOR\HHVLQDFRPSDQ\WKDWPDNHPRUHWKDQFDQUHWULHYHPDQ\
HPSOR\HHV

PROGRAMMER’S GUIDE 123


CHAPTER 6 WORKING WITH DATA

%HFDXVHKRVWYDULDEOHVFDQRQO\KROGDVLQJOHFROXPQYDOXHDWDWLPHDTXHU\WKDWUHWXUQV
PXOWLSOHURZVPXVWEXLOGDWHPSRUDU\WDEOHLQPHPRU\FDOOHGDUHVXOWVWDEOHIURPZKLFKURZV
FDQWKHQEHH[WUDFWHGDQGSURFHVVHGRQHDWDWLPHLQVHTXHQWLDORUGHU64/NHHSVWUDFNRI
WKHQH[WURZWRSURFHVVLQWKHUHVXOWVWDEOHE\HVWDEOLVKLQJDSRLQWHUWRLWFDOOHGDFXUVRU

,03257$17 ,QG\QDPLF64/ '64/ WKHSURFHVVIRUFUHDWLQJDTXHU\DQGUHWULHYLQJGDWDLVVRPHZKDW


GLIIHUHQW)RUPRUHLQIRUPDWLRQDERXWPXOWLURZVHOHFWLRQLQ'64/VHH´6HOHFWLQJPXOWLSOH
URZVLQ'64/µRQSDJH 
7RUHWULHYHPXOWLSOHURZVLQWRDUHVXOWVWDEOHHVWDEOLVKDFXUVRULQWRWKHWDEOHDQGSURFHVV
LQGLYLGXDOURZVLQWKHWDEOH64/SURYLGHVWKHIROORZLQJVHTXHQFHRIVWDWHPHQWV
 '(&/$5(&85625HVWDEOLVKHVDQDPHIRUWKHFXUVRUDQGVSHFLILHVWKHTXHU\WR
SHUIRUP
 23(1H[HFXWHVWKHTXHU\EXLOGVWKHUHVXOWVWDEOHDQGSRVLWLRQVWKHFXUVRUDWWKH
VWDUWRIWKHWDEOH
 )(7&+UHWULHYHVDVLQJOHURZDWDWLPHIURPWKHUHVXOWVWDEOHLQWRKRVWYDULDEOHV
IRUSURJUDPSURFHVVLQJ
 &/26(UHOHDVHVV\VWHPUHVRXUFHVZKHQDOOURZVDUHUHWULHYHG

,03257$17 7RVHOHFWGDWDIURPDWDEOHDXVHUPXVWKDYH6(/(&7SULYLOHJHIRUDWDEOHRUDVWRUHG
SURFHGXUHLQYRNHGE\WKHXVHU·VDSSOLFDWLRQPXVWKDYH6(/(&7SULYLOHJHIRULW

Declaring a cursor
7RGHFODUHDFXUVRUDQGVSHFLI\URZVRIGDWDWRUHWULHYHXVHWKH'(&/$5(
&85625VWDWHPHQW'(&/$5(&85625LVDGHVFULSWLYHQRQH[HFXWDEOHVWDWHPHQW,QWHU%DVH
XVHVWKHLQIRUPDWLRQLQWKHVWDWHPHQWWRSUHSDUHV\VWHPUHVRXUFHVIRUWKHFXUVRUZKHQLWLV
RSHQHGEXWGRHVQRWDFWXDOO\SHUIRUPWKHTXHU\%HFDXVH'(&/$5(&85625LV
QRQH[HFXWDEOH64/&2'(LVQRWDVVLJQHGZKHQWKLVVWDWHPHQWLVXVHG
7KHV\QWD[IRU'(&/$5(&85625LV
DECLARE cursorname CURSOR FOR
SELECT <col> [, <col> ...]
FROM table [, <table> ...]
WHERE <search_condition>
[GROUP BY col [, col ...]]
[HAVING <search_condition>]
[ORDER BY col [ASC | DESC] [, col ...] [ASC | DESC]
| FOR UPDATE OF col [, col ...]];

124 INTERBASE 5
SELECTING MULTIPLE ROWS

7KHFXUVRUQDPHLVXVHGLQVXEVHTXHQW23(1)(7&+DQG&/26(VWDWHPHQWVWRLGHQWLI\WKH
DFWLYHFXUVRU
:LWKWKHIROORZLQJH[FHSWLRQVWKH6(/(&7VWDWHPHQWLQVLGHD'(&/$5(
&85625LVVLPLODUWRDVWDQGDORQH6(/(&7
g $6(/(&7LQD'(&/$5(&85625FDQQRWLQFOXGHDQ,172FODXVH
g $6(/(&7LQD'(&/$5(&85625FDQRSWLRQDOO\LQFOXGHHLWKHUDQ25'(5%<FODXVHRUD
)2583'$7(FODXVH
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWGHFODUHVDFXUVRU
EXEC SQL
DECLARE TO_BE_HIRED CURSOR FOR
SELECT D.DEPARTMENT, D.LOCATION, P.DEPARTMENT
FROM DEPARTMENT D, DEPARTMENT P
WHERE D.MNGR_NO IS NULL
AND D.HEAD_DEPT = P.DEPT_NO;

4 8SGDWLQJWKURXJKFXUVRUV
,QPDQ\DSSOLFDWLRQVGDWDUHWULHYDODQGXSGDWHPD\EHLQWHUGHSHQGHQW'(&/$5(&85625
VXSSRUWVDQRSWLRQDO)2583'$7(FODXVHWKDWRSWLRQDOO\OLVWVFROXPQVLQUHWULHYHGURZVWKDW
FDQEHPRGLILHG)RUH[DPSOHWKHIROORZLQJVWDWHPHQWGHFODUHVVXFKDFXUVRU
EXEC SQL
DECLARE H CURSOR FOR
SELECT CUST_NO
FROM CUSTOMER
WHERE ON_HOLD = "*"
FOR UPDATE OF ON_HOLD;

,IDFROXPQOLVWDIWHU)2583'$7(LVRPLWWHGDOOFROXPQVUHWULHYHGIRUHDFKURZPD\EH
XSGDWHG)RUH[DPSOHWKHIROORZLQJTXHU\HQDEOHVXSGDWLQJIRUWZRFROXPQV
EXEC SQL
DECLARE H CURSOR FOR
SELECT CUST_NAME CUST_NO
FROM CUSTOMER
WHERE ON_HOLD = "*";

)RUPRUHLQIRUPDWLRQDERXWXSGDWLQJFROXPQVWKURXJKDFXUVRUVHH´8SGDWLQJPXOWLSOH
URZVµRQSDJH 

PROGRAMMER’S GUIDE 125


CHAPTER 6 WORKING WITH DATA

Opening a cursor
%HIRUHGDWDVHOHFWHGE\DFXUVRUFDQEHDFFHVVHGWKHFXUVRUPXVWEHRSHQHGZLWKWKH23(1
VWDWHPHQW23(1DFWLYDWHVWKHFXUVRUDQGEXLOGVDUHVXOWVWDEOH,WEXLOGVWKHUHVXOWVWDEOH
EDVHGRQWKHVHOHFWLRQFULWHULDVSHFLILHGLQWKH'(&/$5(&85625VWDWHPHQW7KHURZVLQWKH
UHVXOWVWDEOHFRPSULVHWKHDFWLYHVHWRIWKHFXUVRU
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWRSHQVDSUHYLRXVO\GHFODUHGFXUVRUFDOOHG'(37B(03
EXEC SQL
OPEN DEPT_EMP;

:KHQ,QWHU%DVHH[HFXWHVWKH23(1VWDWHPHQWWKHFXUVRULVSRVLWLRQHGDWWKHVWDUWRIWKHILUVW
URZLQWKHUHVXOWVWDEOH

Fetching rows with a cursor


2QFHDFXUVRULVRSHQHGURZVFDQEHUHWULHYHGRQHDWDWLPHIURPWKHUHVXOWVWDEOHE\XVLQJ
WKH)(7&+VWDWHPHQW)(7&+
 5HWULHYHVWKHQH[WDYDLODEOHURZIURPWKHUHVXOWVWDEOH
 &RSLHVWKRVHURZVLQWRWKHKRVWYDULDEOHVVSHFLILHGLQWKH,172FODXVHRIWKH
)(7&+VWDWHPHQW
 $GYDQFHVWKHFXUVRUWRWKHVWDUWRIWKHQH[WDYDLODEOHURZRUVHWV
64/&2'(WRLQGLFDWLQJWKHFXUVRULVDWWKHHQGRIWKHUHVXOWVWDEOHDQGWKHUH
DUHQRPRUHURZVWRUHWULHYH
7KHFRPSOHWHV\QWD[RIWKH)(7&+VWDWHPHQWLQ64/LV
FETCH <cursorname> INTO :variable [[INDICATOR] :variable]
[, :variable [[INDICATOR] :variable>] ...];

,03257$17 ,QG\QDPLF64/ '64/ PXOWLURZVHOHFWSURFHVVLQJDGLIIHUHQW)(7&+V\QWD[LVXVHG)RU


PRUHLQIRUPDWLRQDERXWUHWULHYLQJPXOWLSOHURZVLQ'64/VHH´)HWFKLQJURZVZLWKD
'64/FXUVRUµRQSDJH 
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWUHWULHYHVDURZIURPWKHUHVXOWVWDEOHIRUWKH
'(37B(03FXUVRUDQGFRSLHVLWVFROXPQYDOXHVLQWRWKHKRVWODQJXDJHYDULDEOHVGHSWQDPH
OQDPHDQGIQDPH
EXEC SQL
FETCH DEPT_EMP
INTO :deptname, :lname, :fname;

126 INTERBASE 5
SELECTING MULTIPLE ROWS

7RSURFHVVHDFKURZLQDUHVXOWVWDEOHLQWKHVDPHPDQQHUHQFORVHWKH)(7&+VWDWHPHQWLQD
KRVWODQJXDJHORRSLQJFRQVWUXFW)RUH[DPSOHWKHIROORZLQJ&FRGHIHWFKHVDQGSULQWVHDFK
URZGHILQHGIRUWKH'(37B(03FXUVRU
. . .
EXEC SQL
FETCH DEPT_EMP
INTO :deptname, :lname, :fname;
while (!SQLCODE)
{
printf("%s %s works in the %s department.\n", fname,
lname, deptname);
EXEC SQL
FETCH DEPT_EMP
INTO :deptname, :lname, :fname;
}
EXEC SQL
CLOSE DEPT_EMP;
. . .

(YHU\)(7&+VWDWHPHQWVKRXOGEHWHVWHGWRVHHLIWKHHQGRIWKHDFWLYHVHWLVUHDFKHG7KH
SUHYLRXVH[DPSOHRSHUDWHVLQWKHFRQWH[WRIDZKLOHORRSWKDWFRQWLQXHVSURFHVVLQJDVORQJ
DV64/&2'(LV]HUR,I64/&2'(LVLWLQGLFDWHVWKDWWKHUHDUHQRPRUHURZVWRUHWULHYH
,I64/&2'(LVOHVVWKDQ]HURLWLQGLFDWHVWKDWDQHUURURFFXUUHG

4 5HWULHYLQJLQGLFDWRUVWDWXV
$Q\FROXPQFDQKDYHD18//YDOXHH[FHSWWKRVHGHILQHGZLWKWKH12718//RU81,48(
LQWHJULW\FRQVWUDLQWV5DWKHUWKDQVWRUHDYDOXHIRUWKHFROXPQ,QWHU%DVHVHWVDIODJLQGLFDWLQJ
WKHFROXPQKDVQRDVVLJQHGYDOXH
7RGHWHUPLQHLIDYDOXHUHWXUQHGIRUDFROXPQLV18//IROORZHDFKYDULDEOHQDPHGLQWKH
,172FODXVHZLWKWKH,1',&$725NH\ZRUGDQGWKHQDPHRIDVKRUWLQWHJHUYDULDEOHFDOOHG
DQLQGLFDWRUYDULDEOHZKHUH,QWHU%DVHVKRXOGVWRUHWKHVWDWXVRIWKH18//YDOXHIODJIRUWKH
FROXPQ,IWKHYDOXHUHWULHYHGLV
g 18//WKHLQGLFDWRUYDULDEOHLVVHWWR²
g 1RW18//WKHLQGLFDWRUSDUDPHWHULVVHWWR
)RUH[DPSOHWKHIROORZLQJ&FRGHGHFODUHVWKUHHKRVWODQJXDJHYDULDEOHVGHSDUWPHQWPDQDJHU
DQGPLVVLQJBPDQDJHUWKHQUHWULHYHVFROXPQYDOXHVLQWR
GHSDUWPHQWPDQDJHUDQGDVWDWXVIODJIRUWKHFROXPQUHWULHYHGLQWRPDQDJHUPLVVLQJBPDQDJHU
ZLWKD)(7&+IURPDSUHYLRXVO\GHFODUHGFXUVRU*(7&,7<
. . .
char department[26];

PROGRAMMER’S GUIDE 127


CHAPTER 6 WORKING WITH DATA

char manager[36];
short missing_manager;
. . .
FETCH GETCITY INTO :department, :manager INDICATOR :missing_manager;

7KHRSWLRQDO,1',&$725NH\ZRUGFDQEHRPLWWHG
FETCH GETCITY INTO :department, :manager :missing_manager;

2IWHQWKHVSDFHEHWZHHQWKHYDULDEOHWKDWUHFHLYHVWKHDFWXDOFRQWHQWVRID
FROXPQDQGWKHYDULDEOHWKDWKROGVWKHVWDWXVRIWKH18//YDOXHIODJLVDOVRRPLWWHG
FETCH GETCITY INTO :department, :manager:missing_manager;
Note :KLOH,QWHU%DVHHQIRUFHVWKH64/UHTXLUHPHQWWKDWWKHQXPEHURIKRVWYDULDEOHVLQD
)(7&+PXVWHTXDOWKHQXPEHURIFROXPQVVSHFLILHGLQ'(&/$5(&85625LQGLFDWRU
YDULDEOHVLQD)(7&+VWDWHPHQWDUHQRWFRXQWHGWRZDUGWKHFROXPQFRXQW

4 5HIHWFKLQJURZVZLWKDFXUVRU
7KHRQO\VXSSRUWHGFXUVRUPRYHPHQWLVIRUZDUGLQVHTXHQWLDORUGHUWKURXJKWKHDFWLYHVHW
7RUHYLVLWSUHYLRXVO\IHWFKHGURZVFORVHWKHFXUVRUDQGWKHQUHRSHQLWZLWKDQRWKHU23(1
VWDWHPHQW)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVFORVHWKH'(37B(03FXUVRUWKHQUHFUHDWH
LWHIIHFWLYHO\UHSRVLWLRQLQJWKHFXUVRUDWWKHVWDUWRIWKH'(37B(03UHVXOWVWDEOH
EXEC SQL
CLOSE DEPT_EMP;
EXEC SQL
OPEN DEPT_EMP;

Closing the cursor


:KHQWKHHQGRIDFXUVRU·VDFWLYHVHWLVUHDFKHGDFXUVRUVKRXOGEHFORVHGWRIUHHXSV\VWHP
UHVRXUFHV7RFORVHDFXUVRUXVHWKH&/26(VWDWHPHQW)RUH[DPSOHWKHIROORZLQJVWDWHPHQW
FORVHVWKH'(37B(03FXUVRU
EXEC SQL
CLOSE DEPT_EMP;

3URJUDPVFDQFKHFNIRUWKHHQGRIWKHDFWLYHVHWE\H[DPLQLQJ64/&2'(ZKLFKLVVHWWR
WRLQGLFDWHWKHUHDUHQRPRUHURZVWRUHWULHYH

128 INTERBASE 5
SELECTING MULTIPLE ROWS

A complete cursor example


7KHIROORZLQJSURJUDPGHFODUHVDFXUVRURSHQVWKHFXUVRUDQGWKHQORRSVWKURXJKWKH
FXUVRU·VDFWLYHVHWIHWFKLQJDQGSULQWLQJYDOXHV7KHSURJUDPFORVHVWKHFXUVRUZKHQDOO
SURFHVVLQJLVILQLVKHGRUDQHUURURFFXUV
#include <stdio.h>
EXEC SQL
BEGIN DECLARE SECTION;
char deptname[26];
char lname[16];
char fname[11];
EXEC SQL
END DECLARE SECTION;

main ()
{
EXEC SQL
WHENEVER SQLERROR GO TO abend;
EXEC SQL
DECLARE DEPT_EMP CURSOR FOR
SELECT DEPARTMENT, LAST_NAME, FIRST_NAME
FROM DEPARTMENT D, EMPLOYEE E
WHERE D.DEPT_NO = E.DEPT_NO"
ORDER BY DEPARTMENT, LAST_NAME, FIRST_NAME;
EXEC SQL
OPEN DEPT_EMP;
EXEC SQL
FETCH DEPT_EMP
INTO :deptname, :lname, :fname;
while (!SQLCODE)
{
printf("%s %s works in the %s department.\n",fname,
lname, deptname);
EXEC SQL
FETCH DEPT_EMP
INTO :deptname, :lname, :fname;
}
EXEC SQL
CLOSE DEPT_EMP;
exit();

abend:

PROGRAMMER’S GUIDE 129


CHAPTER 6 WORKING WITH DATA

if (SQLCODE)
{
isc_print_sqlerror();
EXEC SQL
ROLLBACK;
EXEC SQL
CLOSE_DEPT_EMP;
EXEC SQL
DISCONNECT ALL;
exit(1)
}
else
{
EXEC SQL
COMMIT;
EXEC SQL
DISCONNECT ALL;
exit()
}
}

Selecting rows with NULL values


$Q\FROXPQFDQKDYH18//YDOXHVH[FHSWWKRVHGHILQHGZLWKWKH12718//RU81,48(
LQWHJULW\FRQVWUDLQWV5DWKHUWKDQVWRUHDYDOXHIRUWKHFROXPQ,QWHU%DVHVHWVDIODJLQGLFDWLQJ
WKHFROXPQKDVQRDVVLJQHGYDOXH
8VH,618//LQD:+(5(FODXVHVHDUFKFRQGLWLRQWRTXHU\IRU18//YDOXHV)RUH[DPSOH
VRPHURZVLQWKH'(3$570(17WDEOHGRQRWKDYHDYDOXHIRUWKH
%8'*(7FROXPQ'HSDUWPHQWVZLWKQRVWRUHGEXGJHWKDYHWKH18//YDOXHIODJVHWIRUWKDW
FROXPQ7KHIROORZLQJFXUVRUGHFODUDWLRQUHWULHYHVURZVIRUGHSDUWPHQWVZLWKRXWEXGJHWVIRU
SRVVLEOHXSGDWH
EXEC SQL
DECLARE NO_BUDGET CURSOR FOR
SELECT DEPARTMENT, BUDGET
FROM DEPARTMENT
WHERE BUDGET IS NULL
FOR UPDATE OF BUDGET;

Note 7RGHWHUPLQHLIDFROXPQKDVD18//YDOXHXVHDQLQGLFDWRUYDULDEOH)RUPRUH
LQIRUPDWLRQDERXWLQGLFDWRUYDULDEOHVVHH´5HWULHYLQJLQGLFDWRUVWDWXVµRQSDJH 

130 INTERBASE 5
SELECTING MULTIPLE ROWS

$GLUHFWTXHU\RQDFROXPQFRQWDLQLQJD18//YDOXHUHWXUQV]HURIRUQXPEHUVEODQNVIRU
FKDUDFWHUVDQG1RYHPEHUIRUGDWHV)RUH[DPSOHWKHIROORZLQJFXUVRUGHFODUDWLRQ
UHWULHYHVDOOGHSDUWPHQWEXGJHWVHYHQWKRVHZLWK18//YDOXHVZKLFKDUHUHSRUWHGDV]HUR
EXEC SQL
DECLARE ALL_BUDGETS CURSOR FOR
SELECT DEPARTMENT, BUDGET
FROM DEPARTMENT
ORDER BY BUDGET DESCENDING;

4 /LPLWDWLRQVRQ18//YDOXHV
%HFDXVH,QWHU%DVHWUHDWV18//YDOXHVDVQRQYDOXHVWKHIROORZLQJOLPLWDWLRQVRQ18//
YDOXHVLQTXHULHVVKRXOGEHQRWHG
g 5RZVZLWK18//YDOXHVDUHVRUWHGDIWHUDOORWKHUURZV
g 18//YDOXHVDUHVNLSSHGE\DOODJJUHJDWHRSHUDWLRQVH[FHSWIRU&2817 
g 18//YDOXHVFDQQRWEHHOLFLWHGE\DQHJDWHGWHVWLQDVHDUFKFRQGLWLRQ
g 18//YDOXHVFDQQRWVDWLVI\DMRLQFRQGLWLRQ
18//YDOXHVFDQEHWHVWHGLQFRPSDULVRQV,IDYDOXHRQHLWKHUVLGHRIDFRPSDULVRQRSHUDWRU
LV18//WKHUHVXOWRIWKHFRPSDULVRQLV8QNQRZQ
)RUWKH%RROHDQRSHUDWRUV 127$1'DQG25 WKHIROORZLQJFRQVLGHUDWLRQVDUHPDGH
g 18//YDOXHVZLWK127DOZD\VUHWXUQV8QNQRZQ
g 18//YDOXHVZLWK$1'UHWXUQ8QNQRZQXQOHVVRQHRSHUDQGIRU$1'LVIDOVH,QWKLVODWWHU
FDVH)DOVHLVUHWXUQHG
g 18//YDOXHVZLWK25UHWXUQ8QNQRZQXQOHVVRQHRSHUDQGIRU25LVWUXH,QWKLVODWWHUFDVH
7UXHLVUHWXUQHG
)RULQIRUPDWLRQDERXWGHILQLQJDOWHUQDWH18//YDOXHVVHHWKH'DWD'HILQLWLRQ*XLGH

Selecting rows through a view


7RVHOHFWDVXEVHWRIURZVDYDLODEOHWKURXJKDYLHZVXEVWLWXWHWKHQDPHRIWKHYLHZIRUDWDEOH
QDPHLQWKH)520FODXVHRID6(/(&7)RUH[DPSOHWKHIROORZLQJFXUVRUSURGXFHVDOLVWRI
HPSOR\HHSKRQHQXPEHUVEDVHGRQWKH3+21(B9,(:YLHZ
EXEC SQL
DECLARE PHONE_LIST CURSOR FOR
SELECT FIRST_NAME, LAST_NAME, PHONE_EXT
FROM PHONE_VIEW
WHERE EMPLOYEE.DEPT_NO = DEPARTMENT.DEPT_NO;

PROGRAMMER’S GUIDE 131


CHAPTER 6 WORKING WITH DATA

$YLHZFDQEHDMRLQ9LHZVFDQDOVREHXVHGLQMRLQVWKHPVHOYHVLQSODFHRIWDEOHV)RUPRUH
LQIRUPDWLRQDERXWYLHZVLQMRLQVVHH´-RLQLQJWDEOHVµRQSDJH 

Selecting multiple rows in DSQL


,Q'64/XVHUVDUHXVXDOO\SHUPLWWHGWRVSHFLI\TXHULHVDWUXQWLPH7RDFFRPPRGDWHDQ\
W\SHRITXHU\WKHXVHUVXSSOLHV'64/UHTXLUHVWKHXVHRIH[WHQGHG64/GHVFULSWRUDUHDV
;64/'$V ZKHUHDTXHU\·VLQSXWDQGRXWSXWFDQEHSUHSDUHGDQGGHVFULEHG)RUTXHULHV
UHWXUQLQJPXOWLSOHURZV'64/VXSSRUWVYDULDWLRQVRIWKH'(&/$5(&8562523(1DQG
)(7&+VWDWHPHQWVWKDWPDNHXVHRIWKH;64/'$
7RUHWULHYHPXOWLSOHURZVLQWRDUHVXOWVWDEOHHVWDEOLVKDFXUVRULQWRWKHWDEOHDQGSURFHVV
LQGLYLGXDOURZVLQWKHWDEOH'64/SURYLGHVWKHIROORZLQJVHTXHQFHRIVWDWHPHQWV
 35(3$5(HVWDEOLVKHVWKHXVHUGHILQHGTXHU\VSHFLILFDWLRQLQWKH;64/'$
VWUXFWXUHXVHGIRURXWSXW
 '(&/$5(&85625HVWDEOLVKHVDQDPHIRUWKHFXUVRUDQGVSHFLILHVWKHTXHU\WR
SHUIRUP
 23(1H[HFXWHVWKHTXHU\EXLOGVWKHUHVXOWVWDEOHDQGSRVLWLRQVWKHFXUVRUDWWKH
VWDUWRIWKHWDEOH
 )(7&+UHWULHYHVDVLQJOHURZDWDWLPHIURPWKHUHVXOWVWDEOHIRUSURJUDP
SURFHVVLQJ
 &/26(UHOHDVHVV\VWHPUHVRXUFHVZKHQDOOURZVDUHUHWULHYHG
7KHIROORZLQJWKUHHVHFWLRQVGHVFULEHKRZWRGHFODUHD'64/FXUVRUKRZWRRSHQLWDQG
KRZWRIHWFKURZVXVLQJWKHFXUVRU)RUPRUHLQIRUPDWLRQDERXWFUHDWLQJDQGILOOLQJ;64/'$
VWUXFWXUHVDQGSUHSDULQJ'64/TXHULHVZLWK35(3$5(VHH&KDSWHU´8VLQJ'\QDPLF
64/µ)RUPRUHLQIRUPDWLRQDERXWFORVLQJDFXUVRUVHH´&ORVLQJWKHFXUVRUµRQSDJH 

Declaring a DSQL cursor


'64/PXVWGHFODUHDFXUVRUEDVHGRQDXVHUGHILQHG6(/(&7VWDWHPHQW8VXDOO\'64/
SURJUDPV
g 3URPSWWKHXVHUIRUDTXHU\ 6(/(&7 
g 6WRUHWKHTXHU\LQDKRVWODQJXDJHYDULDEOH
g ,VVXHD35(3$5(VWDWHPHQWWKDWXVHVWKHKRVWODQJXDJHYDULDEOHWRGHVFULEHWKHTXHU\UHVXOWV
LQDQ;64/'$

132 INTERBASE 5
SELECTING MULTIPLE ROWS IN DSQL

g 'HFODUHDFXUVRUXVLQJWKHTXHU\DOLDV
7KHFRPSOHWHV\QWD[IRU'(&/$5(&85625LQ'64/LV
DECLARE cursorname CURSOR FOR queryname;

)RUH[DPSOHWKHIROORZLQJ&FRGHIUDJPHQWGHFODUHVDVWULQJYDULDEOH
TXHU\VWULQJWRKROGWKHXVHUGHILQHGTXHU\JHWVDTXHU\IURPWKHXVHUDQGVWRUHVLWLQ
TXHU\VWULQJXVHVTXHU\VWULQJWR35(3$5(DTXHU\FDOOHG48(5<WKHQGHFODUHVDFXUVRU&WKDW
XVHV48(5<
. . .
EXEC SQL
BEGIN DECLARE SECTION;
char querystring [512];
XSQLDA *InputSqlda, *OutputSqlda;
EXEC SQL
END DECLARE SECTION;
. . .
printf("Enter query: "); /* prompt for query from user */
gets(querystring); /* get the string, store in querystring */
. . .
EXEC SQL
PREPARE QUERY INTO OutputSqlda FROM :querystring;
. . .
EXEC SQL
DECLARE C CURSOR FOR QUERY;

)RUPRUHLQIRUPDWLRQDERXWFUHDWLQJDQGILOOLQJ;64/'$VWUXFWXUHVDQGSUHSDULQJ'64/
TXHULHVZLWK35(3$5(VHH&KDSWHU´8VLQJ'\QDPLF64/µ

Opening a DSQL cursor


7KH23(1VWDWHPHQWLQ'64/HVWDEOLVKHVDUHVXOWVWDEOHIURPWKHLQSXWSDUDPHWHUVVSHFLILHG
LQDSUHYLRXVO\GHFODUHGDQGSRSXODWHG;64/'$$FXUVRUPXVWEHRSHQHGEHIRUHGDWDFDQ
EHUHWULHYHG7KHV\QWD[IRUD'64/23(1LV
OPEN cursorname USING DESCRIPTOR sqldaname;

)RUH[DPSOHWKHIROORZLQJVWDWHPHQWRSHQVWKHFXUVRU&XVLQJWKH;64/'$,QSXW6TOGD
EXEC SQL
OPEN C USING DESCRIPTOR InputSqlda;

PROGRAMMER’S GUIDE 133


CHAPTER 6 WORKING WITH DATA

Fetching rows with a DSQL cursor


'64/XVHVWKH)(7&+VWDWHPHQWWRUHWULHYHURZVIURPDUHVXOWVWDEOH7KHURZVDUHUHWULHYHG
DFFRUGLQJWRVSHFLILFDWLRQVSURYLGHGLQDSUHYLRXVO\HVWDEOLVKHGDQGSRSXODWHGH[WHQGHG64/
GHVFULSWRUDUHD ;64/'$ WKDWGHVFULEHVWKHXVHU·VUHTXHVW7KHV\QWD[IRUWKH'64/)(7&+
VWDWHPHQWLV
FETCH cursorname USING DESCRIPTOR descriptorname;

)RUH[DPSOHWKHIROORZLQJ&FRGHIUDJPHQWGHFODUHV;64/'$VWUXFWXUHVIRULQSXWDQG
RXWSXWDQGLOOXVWUDWHVKRZWKHRXWSXWVWUXFWXUHLVXVHGLQD)(7&+VWDWHPHQW
. . .
XSQLDA *InputSqlda, *OutputSqlda;
. . .
EXEC SQL
FETCH C USING DESCRIPTOR OutputSqlda;
. . .

)RUPRUHLQIRUPDWLRQDERXWFUHDWLQJDQGILOOLQJ;64/'$VWUXFWXUHVDQGSUHSDULQJ'64/
TXHULHVZLWK35(3$5(VHH&KDSWHU´8VLQJ'\QDPLF64/µ

Joining tables
-RLQVHQDEOHUHWULHYDORIGDWDIURPWZRRUPRUHWDEOHVLQDGDWDEDVHZLWKDVLQJOH6(/(&77KH
WDEOHVIURPZKLFKGDWDLVWREHH[WUDFWHGDUHOLVWHGLQWKH)520FODXVH2SWLRQDOV\QWD[LQWKH
)520FODXVHFDQUHGXFHWKHQXPEHURIURZVUHWXUQHGDQGDGGLWLRQDO:+(5(FODXVHV\QWD[
FDQIXUWKHUUHGXFHWKHQXPEHURIURZVUHWXUQHG
)URPWKHLQIRUPDWLRQLQD6(/(&7WKDWGHVFULEHVDMRLQ,QWHU%DVHEXLOGVDWDEOHWKDWFRQWDLQV
WKHUHVXOWVRIWKHMRLQRSHUDWLRQWKHUHVXOWVWDEOHVRPHWLPHVDOVRFDOOHGDG\QDPLFRUYLUWXDOWDEOH
,QWHU%DVHVXSSRUWVWZREDVLFW\SHVRIMRLQV
g ,QQHUMRLQVOLQNURZVLQWDEOHVEDVHGRQVSHFLILHGMRLQFRQGLWLRQVDQGUHWXUQRQO\WKRVHURZV
WKDWPDWFKWKHMRLQFRQGLWLRQV7KHUHDUHWKUHHW\SHVRILQQHUMRLQV
à (TXLMRLQVOLQNURZVEDVHGRQFRPPRQYDOXHVRUHTXDOLW\UHODWLRQVKLSVLQWKHMRLQFROXPQV
à -RLQVWKDWOLQNURZVEDVHGRQFRPSDULVRQVRWKHUWKDQHTXDOLW\LQWKHMRLQFROXPQV7KHUHLV
QRWDQRIILFLDOO\UHFRJQL]HGQDPHIRUWKHVHW\SHVRIMRLQVEXWIRUVLPSOLFLW\·VVDNHWKH\PD\
EHFDWHJRUL]HGDVFRPSDUDWLYHMRLQVRUQRQHTXLMRLQV
à 5HIOH[LYHRUVHOIMRLQVFRPSDUHYDOXHVZLWKLQDFROXPQRIDVLQJOHWDEOH

134 INTERBASE 5
JOINING TABLES

g 2XWHUMRLQVOLQNURZVLQWDEOHVEDVHGRQVSHFLILHGMRLQFRQGLWLRQVDQGUHWXUQERWKURZVWKDW
PDWFKWKHMRLQFRQGLWLRQVDQGDOORWKHUURZVIURPRQHRUPRUHWDEOHVHYHQLIWKH\GRQRW
PDWFKWKHMRLQFRQGLWLRQ
7KHPRVWFRPPRQO\XVHGMRLQVDUHLQQHUMRLQVEHFDXVHWKH\ERWKUHVWULFWWKHGDWDUHWXUQHG
DQGVKRZDFOHDUUHODWLRQVKLSEHWZHHQWZRRUPRUHWDEOHV2XWHUMRLQVKRZHYHUDUHXVHIXO
IRUYLHZLQJMRLQHGURZVDJDLQVWDEDFNJURXQGRIURZVWKDWGRQRWPHHWWKHMRLQFRQGLWLRQV

Choosing join columns


5HJDUGOHVVRIMRLQW\SHVWRFUHDWHDXVHIXOMRLQWKHFROXPQVWKDWDUHFRPSDUHGVKRXOGEHD
35,0$5<.(<RUD)25(,*1.(<-RLQHGFROXPQVQHHGQRWKDYHWKHVDPHQDPHVEXWWKH\
PXVWEHRIFRPSDWLEOHGDWDW\SHV)RUH[DPSOH,17(*(5'(&,0$/180(5,&DQG)/2$7
GDWDW\SHVFDQEHFRPSDUHGWRRQHDQRWKHUEHFDXVHWKH\DUHDOOQXPEHUV6WULQJYDOXHVOLNH
&+$5DQG9$5&+$5FDQRQO\EHFRPSDUHGWRRWKHUVWULQJYDOXHVXQOHVVWKH\FRQWDLQ$6&,,
YDOXHVWKDWDUHDOOQXPEHUV7KH&$67 IXQFWLRQFDQEHXVHGWRIRUFHWUDQVODWLRQRIRQH
,QWHU%DVHGDWDW\SHWRDQRWKHUIRUFRPSDULVRQV)RUPRUHLQIRUPDWLRQDERXW&$67 VHH
´8VLQJ&$67 IRUGDWDW\SHFRQYHUVLRQVµRQSDJH 

,03257$17 ,IDMRLQHGFROXPQFRQWDLQVD18//YDOXHIRUDJLYHQURZ,QWHU%DVHGRHVQRWLQFOXGHWKDW
URZLQWKHUHVXOWVWDEOHXQOHVVSHUIRUPLQJDQRXWHUMRLQ

Using inner joins


,QWHU%DVHVXSSRUWVWZRPHWKRGVIRUFUHDWLQJLQQHUMRLQV)RUSRUWDELOLW\DQGFRPSDWLELOLW\
ZLWKH[LVWLQJ64/DSSOLFDWLRQV,QWHU%DVHFRQWLQXHVWRVXSSRUWWKHROG64/PHWKRGIRU
VSHFLI\LQJMRLQV,QROGHUYHUVLRQVRI64/WKHUHLVQRH[SOLFLWMRLQODQJXDJH$QLQQHUMRLQLV
VSHFLILHGE\OLVWLQJWDEOHVWRMRLQLQWKH)520FODXVHRID6(/(&7DQGWKHFROXPQVWR
FRPSDUHLQWKH:+(5(FODXVH
)RUH[DPSOHWKHIROORZLQJMRLQUHWXUQVWKHGHSDUWPHQWQDPHPDQDJHUQXPEHUDQGVDODU\
IRUDQ\PDQDJHUZKRVHVDODU\DFFRXQWVIRURQHWKLUGRUPRUHRIWKHWRWDOVDODULHVRI
HPSOR\HHVLQWKDWGHSDUWPHQW
EXEC SQL
DECLARE BIG_SAL CURSOR FOR
SELECT D.DEPARTMENT, D.MNGR_NO, E.SALARY
FROM DEPARTMENT D, EMPLOYEE E
WHERE D.MNGR_NO = E.EMP_NO AND E.SALARY*2
>= (SELECT SUM(S.SALARY) FROM EMPLOYEE S
WHERE D.DEPT_NO = S.DEPT_NO)
ORDER BY D.DEPARTMENT;

PROGRAMMER’S GUIDE 135


CHAPTER 6 WORKING WITH DATA

,QWHU%DVHDOVRLPSOHPHQWVQHZH[SOLFLWMRLQV\QWD[EDVHGRQ64/
SELECT col [, col ...] | *
FROM <tablerefleft> [INNER] JOIN <tablerefright>
[ON <searchcondition>]
[WHERE <searchcondition>];

7KHMRLQLVH[SOLFLWO\GHFODUHGLQWKH)520FODXVHXVLQJWKH-2,1NH\ZRUG7KHWDEOHUHIHUHQFH
DSSHDULQJWRWKHOHIWRIWKH-2,1NH\ZRUGLVFDOOHGWKHOHIWWDEOHZKLOHWKHWDEOHWRWKHULJKWRI
WKH-2,1LVFDOOHGWKHULJKWWDEOH6HDUFKFRQGLWLRQVEDVHGRQDFROXPQLQWKHULJKWWDEOHFDQEH
VSHFLILHGLQDQRSWLRQDO21FODXVHIROORZLQJWKHULJKWWDEOHUHIHUHQFH)RUH[DPSOHXVLQJWKH
QHZMRLQV\QWD[WKHSUHYLRXVO\GHVFULEHGTXHU\FDQEHUHZULWWHQDV
EXEC SQL
DECLARE BIG_SAL CURSOR FOR
SELECT D.DEPARTMENT, D.MNGR_NO, E.SALARY
FROM DEPARTMENT D INNER JOIN EMPLOYEE E
ON D.MNGR_NO = E.EMP_NO
AND E.SALARY*2 > (SELECT SUM(S.SALARY) FROM EMPLOYEE S
WHERE D.DEPT_NO = S.DEPT_NO)
ORDER BY D.DEPARTMENT;

The new join syntax offers several advantages. An explicit join declaration
makes the intention of the program clear when reading its source code.
7KH21FODXVHHQDEOHVMRLQVHDUFKFRQGLWLRQVWREHH[SUHVVHGLQWKH)520FODXVH7KHVHDUFK
FRQGLWLRQWKDWIROORZVWKH21FODXVHLVWKHRQO\SODFHZKHUHUHWULHYDORIURZVFDQEH
UHVWULFWHGEDVHGRQFROXPQVDSSHDULQJLQWKHULJKWWDEOH7KH:+(5(FODXVHFDQEHXVHGWR
IXUWKHUUHVWULFWURZVEDVHGVROHO\RQFROXPQVLQWKHOHIWWDEOH
7KH)520FODXVHDOVRSHUPLWVWKHXVHRIWDEOHUHIHUHQFHVSDUHQWKHWLFDOQHVWHGMRLQVZKRVH
UHVXOWWDEOHVDUHFUHDWHGDQGWKHQSURFHVVHGDVLIWKH\ZHUHDFWXDOWDEOHVVWRUHGLQDGDWDEDVH
)RUPRUHLQIRUPDWLRQDERXWQHVWHGMRLQVVHH´8VLQJQHVWHGMRLQVµRQSDJH 

4 &UHDWLQJHTXLMRLQV
$QLQQHUMRLQWKDWPDWFKHVYDOXHVLQMRLQFROXPQVLVFDOOHGDQHTXLMRLQ(TXLMRLQVDUHDPRQJ
WKHPRVWFRPPRQMRLQRSHUDWLRQV7KH21FODXVHLQDQHTXLMRLQDOZD\VWDNHVWKHIRUP
ON t1.column = t2.column

)RUH[DPSOHWKHIROORZLQJMRLQUHWXUQVDOLVWRIFLWLHVDURXQGWKHZRUOGLIWKHFDSLWDOFLWLHV
DOVRDSSHDULQWKH&,7,(6WDEOHDQGDOVRUHWXUQVWKHSRSXODWLRQVRIWKRVHFLWLHV
EXEC SQL
DECLARE CAPPOP CURSOR FOR
SELECT COU.NAME, COU.CAPITAL, CIT.POPULATION
FROM COUNTRIES COU JOIN CITIES CIT ON CIT.NAME = COU.CAPITAL

136 INTERBASE 5
JOINING TABLES

WHERE COU.CAPITAL NOT NULL


ORDER BY COU.NAME;

,QWKLVH[DPSOHWKH21FODXVHVSHFLILHVWKDWWKH&,7,(6WDEOHPXVWFRQWDLQDFLW\QDPHWKDW
PDWFKHVDFDSLWDOQDPHLQWKH&28175,(6WDEOHLIDURZLVWREHUHWXUQHG1RWHWKDWWKH
:+(5(FODXVHUHVWULFWVURZVUHWULHYHGIURPWKH&28175,(6WDEOHWRWKRVHZKHUHWKH
&$3,7$/FROXPQFRQWDLQVDYDOXH

4 -RLQVEDVHGRQFRPSDULVRQRSHUDWRUV
,QQHUMRLQVFDQFRPSDUHYDOXHVLQMRLQFROXPQVXVLQJRWKHUFRPSDULVRQRSHUDWRUVEHVLGHVWKH
HTXDOLW\RSHUDWRU)RUH[DPSOHDMRLQPLJKWEHEDVHGRQDFROXPQLQRQHWDEOHKDYLQJDYDOXH
OHVVWKDQWKHYDOXHLQDFROXPQLQDQRWKHUWDEOH7KH21FODXVHLQDFRPSDULVRQMRLQDOZD\V
WDNHVWKHIRUP
ON t1.column <operator> t2.column

ZKHUHRSHUDWRU!LVDYDOLGFRPSDULVRQRSHUDWRU)RUDOLVWRIYDOLGFRPSDULVRQRSHUDWRUVVHH
´8VLQJFRPSDULVRQRSHUDWRUVLQH[SUHVVLRQVµRQSDJH 
)RUH[DPSOHWKHIROORZLQJMRLQUHWXUQVLQIRUPDWLRQDERXWSURYLQFHVLQ&DQDGDWKDWDUHODUJHU
WKDQWKHVWDWHRI$ODVNDLQWKH8QLWHG6WDWHV
EXEC SQL
DECLARE BIGPROVINCE CURSOR FOR
SELECT S.STATE_NAME, S.AREA, P.PROVINCE_NAME, P.AREA
FROM STATES S JOIN PROVINCE P ON P.AREA > S.AREA AND
P.COUNTRY = "Canada"
WHERE S.STATE_NAME = "Alaska";

,QWKLVH[DPSOHWKHILUVWFRPSDULVRQRSHUDWRULQWKH21FODXVHWHVWVWRVHHLIWKHDUHDRID
SURYLQFHLVJUHDWHUWKDQWKHDUHDRIDQ\VWDWH WKH:+(5(FODXVHUHVWULFWVILQDORXWSXWWR
GLVSOD\RQO\LQIRUPDWLRQIRUSURYLQFHVWKDWDUHODUJHULQDUHDWKDQWKHVWDWHRI$ODVND 

4 &UHDWLQJVHOIMRLQV
$VHOIMRLQLVDQLQQHUMRLQZKHUHDWDEOHLVMRLQHGWRLWVHOIWRFRUUHODWHFROXPQVRIGDWD)RU
H[DPSOHWKH5,9(56WDEOHOLVWVULYHUVE\QDPHDQGIRUHDFKULYHUOLVWVWKHULYHULQWRZKLFKLW
IORZV1RWDOOULYHUVRIFRXUVHIORZLQWRRWKHUULYHUV7RGLVFRYHUZKLFKULYHUVIORZLQWRRWKHU
ULYHUVDQGZKDWWKHLUQDPHVDUHWKH
5,9(56WDEOHPXVWEHMRLQHGWRLWVHOI
EXEC SQL
DECLARE RIVERSTORIVERS CURSOR FOR
SELECT R1.RIVER, R2.RIVER
FROM RIVERS R1 JOIN RIVERS R2 ON R2.OUTFLOW = R1.RIVER
ORDER BY R1.RIVER, R2.SOURCE;

PROGRAMMER’S GUIDE 137


CHAPTER 6 WORKING WITH DATA

$VWKLVH[DPSOHLOOXVWUDWHVZKHQDWDEOHLVMRLQHGWRLWVHOIHDFKLQYRFDWLRQRIWKHWDEOHPXVW
EHDVVLJQHGDXQLTXHFRUUHODWLRQQDPH 5DQG5DUHFRUUHODWLRQQDPHVLQWKHH[DPSOH )RU
PRUHLQIRUPDWLRQDERXWDVVLJQLQJDQGXVLQJFRUUHODWLRQQDPHVVHH´'HFODULQJDQGXVLQJ
FRUUHODWLRQQDPHVµRQSDJH 

Using outer joins


2XWHUMRLQVSURGXFHDUHVXOWVWDEOHWKDWFRQWDLQVFROXPQVIURPHYHU\URZLQRQHWDEOHDQGD
VXEVHWRIURZVIURPDQRWKHUWDEOH$FWXDOO\RQHW\SHRIRXWHUMRLQUHWXUQVDOOURZVIURPHDFK
WDEOHEXWWKLVW\SHRIMRLQLVXVHGOHVVIUHTXHQWO\WKDQRWKHUW\SHV2XWHUMRLQV\QWD[LVYHU\
VLPLODUWRWKDWRILQQHUMRLQV
SELECT col [, col ...] | *
FROM <tablerefleft> {LEFT | RIGHT | FULL} [OUTER] JOIN
<tablerefright> [ON <searchcondition>]
[WHERE <searchcondition>];

2XWHUMRLQV\QWD[UHTXLUHVWKDW\RXVSHFLI\WKHW\SHRIMRLQWRSHUIRUP7KHUHDUHWKUHH
SRVVLELOLWLHV
g $OHIWRXWHUMRLQUHWULHYHVDOOURZVIURPWKHOHIWWDEOHLQDMRLQDQGUHWULHYHVDQ\URZVIURPWKH
ULJKWWDEOHWKDWPDWFKWKHVHDUFKFRQGLWLRQVSHFLILHGLQWKH21FODXVH
g $ULJKWRXWHUMRLQUHWULHYHVDOOURZVIURPWKHULJKWWDEOHLQDMRLQDQGUHWULHYHVDQ\URZVIURP
WKHOHIWWDEOHWKDWPDWFKWKHVHDUFKFRQGLWLRQVSHFLILHGLQWKH21FODXVH
g $IXOORXWHUMRLQUHWULHYHVDOOURZVIURPERWKWKHOHIWDQGULJKWWDEOHVLQDMRLQUHJDUGOHVVRIWKH
VHDUFKFRQGLWLRQVSHFLILHGLQWKH21FODXVH
2XWHUMRLQVDUHXVHIXOIRUFRPSDULQJDVXEVHWRIGDWDWRWKHEDFNJURXQGRIDOOGDWDIURP
ZKLFKLWLVUHWULHYHG)RUH[DPSOHZKHQOLVWLQJWKRVHFRXQWULHVZKLFKFRQWDLQWKHVRXUFHVRI
ULYHUVLWPD\EHLQWHUHVWLQJWRVHHWKRVHFRXQWULHVZKLFKDUHQRWWKHVRXUFHVRIULYHUVDVZHOO

4 8VLQJDOHIWRXWHUMRLQ
7KHOHIWRXWHUMRLQLVPRUHFRPPRQO\XVHGWKDQRWKHUW\SHVRIRXWHUMRLQV7KHIROORZLQJOHIW
RXWHUMRLQUHWULHYHVWKRVHFRXQWULHVWKDWFRQWDLQWKHVRXUFHVRIULYHUVDQGLGHQWLILHVWKRVH
FRXQWULHVWKDWGRQRWKDYH18//YDOXHVLQWKH55,9(56FROXPQ
EXEC SQL
DECLARE RIVSOURCE CURSOR FOR
SELECT C.COUNTRY, R.RIVER
FROM COUNTRIES C LEFT JOIN RIVERS R ON R.SOURCE = C.COUNTRY
ORDER BY C.COUNTRY;

138 INTERBASE 5
JOINING TABLES

7KH21FODXVHHQDEOHVMRLQVHDUFKFRQGLWLRQVWREHH[SUHVVHGLQWKH)520FODXVH7KH
VHDUFKFRQGLWLRQWKDWIROORZVWKH21FODXVHLVWKHRQO\SODFHZKHUHUHWULHYDORIURZVFDQEH
UHVWULFWHGEDVHGRQFROXPQVDSSHDULQJLQWKHULJKWWDEOH7KH:+(5(FODXVHFDQEHXVHGWR
IXUWKHUUHVWULFWURZVEDVHGVROHO\RQFROXPQVLQWKHOHIW RXWHU WDEOH

4 8VLQJDULJKWRXWHUMRLQ
$ULJKWRXWHUMRLQUHWULHYHVDOOURZVIURPWKHULJKWWDEOHLQDMRLQDQGRQO\WKRVHURZVIURP
WKHOHIWWDEOHWKDWPDWFKWKHVHDUFKFRQGLWLRQVSHFLILHGLQWKH21FODXVH7KHIROORZLQJULJKW
RXWHUMRLQUHWULHYHVDOLVWRIULYHUVDQGWKHLUFRXQWULHVRIRULJLQEXWDOVRUHSRUWVWKRVH
FRXQWULHVWKDWDUHQRWWKHVRXUFHRIDQ\ULYHU
EXEC SQL
DECLARE RIVSOURCE CURSOR FOR
SELECT R.RIVER, C.COUNTRY
FROM RIVERS.R RIGHT JOIN COUNTRIES C ON C.COUNTRY = R.SOURCE
ORDER BY C.COUNTRY;

7,3 0RVWULJKWRXWHUMRLQVFDQEHUHZULWWHQDVOHIWRXWHUMRLQVE\UHYHUVLQJWKHRUGHULQZKLFK
WDEOHVDUHOLVWHG

4 8VLQJDIXOORXWHUMRLQ
$IXOORXWHUMRLQUHWXUQVDOOVHOHFWHGFROXPQVWKDWGRQRWFRQWDLQ18//YDOXHVIURPHDFKWDEOH
LQWKH)520FODXVHZLWKRXWUHJDUGWRVHDUFKFRQGLWLRQV,WLVXVHIXOWRFRQVROLGDWHVLPLODUGDWD
IURPGLVSDUDWHWDEOHV
)RUH[DPSOHVHYHUDOWDEOHVLQDGDWDEDVHPD\FRQWDLQFLW\QDPHV$VVXPLQJWULJJHUVKDYHQRW
EHHQFUHDWHGWKDWHQVXUHWKDWDFLW\HQWHUHGLQRQHWDEOHLVDOVRHQWHUHGLQWKHRWKHUVWRZKLFK
LWDOVRDSSOLHVRQHRIWKHRQO\ZD\VWRVHHDOLVWRIDOOFLWLHVLQWKHGDWDEDVHLVWRXVHIXOORXWHU
MRLQV7KHIROORZLQJH[DPSOHXVHVWZRIXOORXWHUMRLQVWRUHWULHYHWKHQDPHRIHYHU\FLW\OLVWHG
LQWKUHHWDEOHV&28175,(6&,7,(6DQG1$7,21$/B3$5.6
EXEC SQL
DECLARE ALLCITIES CURSOR FOR
SELECT DISTINCT CIT.CITY, COU.CAPITAL, N.PARKCITY
FROM (CITIES CIT FULL JOIN COUNTRIES COU) FULL
JOIN NATIONAL_PARKS N;
7KLVH[DPSOHXVHVDQHVWHGIXOORXWHUMRLQWRSURFHVVDOOURZVIURPWKH&,7,(6DQG&28175,(6
WDEOHV7KHUHVXOWWDEOHSURGXFHGE\WKDWRSHUDWLRQLVWKHQXVHGDVWKHOHIWWDEOHRIWKHIXOO
RXWHUMRLQZLWKWKH1$7,21$/B3$5.6WDEOH)RUPRUHLQIRUPDWLRQDERXWXVLQJQHVWHGMRLQV
VHH´8VLQJQHVWHGMRLQVµRQSDJH 
Note ,QPRVWGDWDEDVHVZKHUHWDEOHVVKDUHVLPLODURUUHODWHGLQIRUPDWLRQWULJJHUVDUHXVXDOO\
FUHDWHGWRHQVXUHWKDWDOOWDEOHVDUHXSGDWHGZLWKVKDUHGLQIRUPDWLRQ)RUPRUHLQIRUPDWLRQ
DERXWWULJJHUVVHHWKH'DWD'HILQLWLRQ*XLGH

PROGRAMMER’S GUIDE 139


CHAPTER 6 WORKING WITH DATA

Using nested joins


7KH6(/(&7VWDWHPHQW)520FODXVHFDQEHXVHGWRVSHFLI\DQ\FRPELQDWLRQRIDYDLODEOH
WDEOHVRUWDEOHUHIHUHQFHVSDUHQWKHWLFDOQHVWHGMRLQVZKRVHUHVXOWVWDEOHVDUHFUHDWHGDQGWKHQ
SURFHVVHGDVLIWKH\ZHUHDFWXDOWDEOHVVWRUHGLQWKHGDWDEDVH7DEOHUHIHUHQFHVDUHIOH[LEOHDQG
SRZHUIXOHQDEOLQJWKHVXFFLQFWFUHDWLRQRIFRPSOH[MRLQVLQDVLQJOHORFDWLRQLQD6(/(&7
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWFRQWDLQVDSDUHQWKHWLFDORXWHUMRLQWKDWFUHDWHVDUHVXOWV
WDEOHZLWKWKHQDPHVRIHYHU\FLW\LQWKH&,7,(6WDEOHHYHQLIWKHFLW\LVQRWDVVRFLDWHGZLWKD
FRXQWU\LQWKH&28175,(6WDEOH7KHUHVXOWVWDEOHLVWKHQSURFHVVHGDVWKHOHIWWDEOHRIDQ
LQQHUMRLQWKDWUHWXUQVRQO\WKRVHFLWLHVWKDWKDYHSURIHVVLRQDOVSRUWVWHDPVRIDQ\NLQGWKH
QDPHRIWKHWHDPDQGWKHVSRUWWKHWHDPSOD\V
DECLARE SPORTSCITIES CURSOR FOR
SELECT COU.COUNTRY, C.CITY, T.TEAM, T.SPORT
FROM (CITIES CIT LEFT JOIN COUNTRIES COU ON COU.COUNTRY =
CIT.COUNTRY) INNER JOIN TEAMS T ON T.CITY = C.CITY
ORDER BY COU.COUNTRY;

)RUPRUHLQIRUPDWLRQDERXWOHIWMRLQVVHH´8VLQJRXWHUMRLQVµRQSDJH 

Using subqueries
$VXETXHU\LVDSDUHQWKHWLFDO6(/(&7VWDWHPHQWQHVWHGLQVLGHWKH:+(5(FODXVHRIDQRWKHU
6(/(&7VWDWHPHQWZKHUHLWIXQFWLRQVDVDVHDUFKFRQGLWLRQWRUHVWULFWWKHQXPEHURIURZV
UHWXUQHGE\WKHRXWHURUSDUHQWTXHU\$VXETXHU\FDQUHIHUWRWKHVDPHWDEOHRUWDEOHVDVLWV
SDUHQWTXHU\RUWRRWKHUWDEOHV
7KHHOHPHQWDU\V\QWD[IRUDVXETXHU\LV
SELECT [DISTINCT] col [, col ...]
FROM <tableref> [, <tableref> ...]
WHERE {expression {[NOT] IN | comparison_operator}
| [NOT] EXISTS} (SELECT [DISTINCT] col [, col ...]
FROM <tableref> [, <tableref> ...]
WHERE <search_condition>);

%HFDXVHDVXETXHU\LVDVHDUFKFRQGLWLRQLWLVXVXDOO\HYDOXDWHGEHIRUHLWVSDUHQWTXHU\ZKLFK
WKHQXVHVWKHUHVXOWWRGHWHUPLQHZKHWKHURUQRWDURZTXDOLILHVIRUUHWULHYDO7KHRQO\
H[FHSWLRQLVWKHFRUUHODWHGVXETXHU\ZKHUHWKHSDUHQWTXHU\SURYLGHVYDOXHVIRUWKHVXETXHU\WR
HYDOXDWH)RUPRUHLQIRUPDWLRQDERXWFRUUHODWHGVXETXHULHVVHH´&RUUHODWHGVXETXHULHVµRQ
SDJH 

140 INTERBASE 5
USING SUBQUERIES

$VXETXHU\GHWHUPLQHVWKHVHDUFKFRQGLWLRQIRUDSDUHQW·V:+(5(FODXVHLQRQHRIWKH
IROORZLQJZD\V
g 3URGXFHVDOLVWRIYDOXHVIRUHYDOXDWLRQE\DQ,1RSHUDWRULQWKHSDUHQWTXHU\·V:+(5(FODXVH
RUZKHUHDFRPSDULVRQRSHUDWRULVPRGLILHGE\WKH$//$1<RU620(RSHUDWRUV
g 5HWXUQVDVLQJOHYDOXHIRUXVHZLWKDFRPSDULVRQRSHUDWRU
g 7HVWVZKHWKHURUQRWGDWDPHHWVFRQGLWLRQVVSHFLILHGE\DQ(;,676RSHUDWRULQWKHSDUHQW
TXHU\·V:+(5(FODXVH
6XETXHULHVFDQEHQHVWHGZLWKLQRWKHUVXETXHULHVDVVHDUFKFRQGLWLRQVHVWDEOLVKLQJDFKDLQ
RISDUHQWFKLOGTXHULHV

Simple subqueries
$VXETXHU\LVHVSHFLDOO\XVHIXOIRUH[WUDFWLQJGDWDIURPDVLQJOHWDEOHZKHQDVHOIMRLQLV
LQDGHTXDWH)RUH[DPSOHLWLVLPSRVVLEOHWRUHWULHYHDOLVWRIWKRVHFRXQWULHVZLWKDODUJHUWKDQ
DYHUDJHDUHDE\MRLQLQJWKH&28175,(6WDEOHWRLWVHOI$VXETXHU\KRZHYHUFDQHDVLO\UHWXUQ
WKDWLQIRUPDWLRQ
EXEC SQL
DECLARE LARGECOUNTRIES CURSOR FOR
SELECT COUNTRY, AREA
FROM COUNTRIES
WHERE AREA > (SELECT AVG(AREA) FROM COUNTRIES);
ORDER BY AREA;

,QWKLVH[DPSOHERWKWKHTXHU\DQGVXETXHU\UHIHUWRWKHVDPHWDEOH4XHULHVDQGVXETXHULHV
FDQUHIHUWRGLIIHUHQWWDEOHVWRR)RUH[DPSOHWKHIROORZLQJTXHU\UHIHUVWRWKH&,7,(6WDEOH
DQGLQFOXGHVDVXETXHU\WKDWUHIHUVWRWKH&28175,(6WDEOH
EXEC SQL
DECLARE EUROCAPPOP CURSOR FOR
SELECT CIT.CITY, CIT.POPULATION
FROM CITIES CIT
WHERE CIT.CITY IN (SELECT COU.CAPITAL FROM COUNTRIES COU
WHERE COU.CONTINENT = "Europe")
ORDER BY CIT.CITY;

7KLVH[DPSOHXVHVFRUUHODWLRQQDPHVWRGLVWLQJXLVKEHWZHHQWDEOHVHYHQWKRXJKWKHTXHU\
DQGVXETXHU\UHIHUHQFHVHSDUDWHWDEOHV&RUUHODWLRQQDPHVDUHRQO\QHFHVVDU\ZKHQERWKD
TXHU\DQGVXETXHU\UHIHUWRWKHVDPHWDEOHVDQGWKRVHWDEOHVVKDUHFROXPQQDPHVEXWLWLV
JRRGSURJUDPPLQJSUDFWLFHWRXVHWKHP)RUPRUHLQIRUPDWLRQDERXWXVLQJFRUUHODWLRQ
QDPHVVHH´'HFODULQJDQGXVLQJFRUUHODWLRQQDPHVµRQSDJH 

PROGRAMMER’S GUIDE 141


CHAPTER 6 WORKING WITH DATA

Correlated subqueries
$FRUUHODWHGVXETXHU\LVDVXETXHU\WKDWGHSHQGVRQLWVSDUHQWTXHU\IRUWKHYDOXHVLWHYDOXDWHV
%HFDXVHHDFKURZHYDOXDWHGE\WKHSDUHQWTXHU\LVSRWHQWLDOO\GLIIHUHQWWKHVXETXHU\LV
H[HFXWHGRQFHIRUHDFKURZSUHVHQWHGWRLWE\WKHSDUHQWTXHU\
)RUH[DPSOHWKHIROORZLQJTXHU\OLVWVHDFKFRXQWU\IRUZKLFKWKHUHDUHWKUHHRUPRUHFLWLHV
VWRUHGLQWKH&,7,(6WDEOH)RUHDFKURZLQWKH&28175,(6WDEOHDFRXQWU\QDPHLVUHWULHYHG
LQWKHSDUHQWTXHU\WKHQXVHGLQWKHFRPSDULVRQRSHUDWLRQLQWKHVXETXHU\·V:+(5(FODXVH
WRYHULI\LIDFLW\LQWKH&,7,(6WDEOHVKRXOGEHFRXQWHGE\WKH&2817 IXQFWLRQ,I&2817 
H[FHHGVIRUDURZWKHURZLVUHWULHYHG
EXEC SQL
DECLARE TRICITIES CURSOR FOR
SELECT COUNTRY
FROM COUNTRIES COU
WHERE 3 <= (SELECT COUNT (*)
FROM CITIES CIT
WHERE CIT.CITY = COU.CAPITAL);

6LPSOHDQGFRUUHODWHGVXETXHULHVFDQEHQHVWHGDQGPL[HGWREXLOGFRPSOH[TXHULHV)RU
H[DPSOHWKHIROORZLQJTXHU\UHWULHYHVWKHFRXQWU\QDPHFDSLWDOFLW\DQGODUJHVWFLW\RI
FRXQWULHVZKRVHDUHDVDUHODUJHUWKDQWKHDYHUDJHDUHDRIFRXQWULHVWKDWKDYHDWOHDVWRQHFLW\
ZLWKLQPHWHUVRIVHDOHYHO
EXEC SQL
DECLARE SEACOUNTRIES CURSOR FOR
SELECT CO1.COUNTRY, C01.CAPITAL, CI1.CITY
FROM COUNTRIES C01, CITIES CI1
WHERE CO1.COUNTRY = CI1.COUNTRY AND CI1.POPULATION =
(SELECT MAX(CI2.POPULATION)
FROM CITIES CI2 WHERE CI2.COUNTRY = CI1.COUNTRY)
AND CO1.AREA >
(SELECT AVG (CO2.AREA)
FROM COUNTRIES C02 WHERE EXISTS
(SELECT *
FROM CITIES CI3 WHERE CI3.COUNTRY = CO2.COUNTRY
AND CI3.ALTITUDE <= 30));

:KHQDWDEOHLVVHSDUDWHO\VHDUFKHGE\TXHULHVDQGVXETXHULHVDVLQWKLVH[DPSOHHDFK
LQYRFDWLRQRIWKHWDEOHPXVWHVWDEOLVKDVHSDUDWHFRUUHODWLRQQDPHIRUWKHWDEOH8VLQJ
FRUUHODWLRQQDPHVLVWKHRQO\PHWKRGWRDVVXUHWKDWFROXPQUHIHUHQFHVDUHDVVRFLDWHGZLWK
DSSURSULDWHLQVWDQFHVRIWKHLUWDEOHV)RUPRUHLQIRUPDWLRQDERXWFRUUHODWLRQQDPHVVHH
´'HFODULQJDQGXVLQJFRUUHODWLRQQDPHVµRQSDJH 

142 INTERBASE 5
INSERTING DATA

Inserting data
1HZURZVRIGDWDDUHDGGHGWRRQHWDEOHDWDWLPHZLWKWKH,16(57VWDWHPHQW7RLQVHUWGDWD
DXVHURUVWRUHGSURFHGXUHPXVWKDYH,16(57SULYLOHJHIRUDWDEOH
7KH,16(57VWDWHPHQWHQDEOHVGDWDLQVHUWLRQIURPWZRGLIIHUHQWVRXUFHV
g $9$/8(6FODXVHWKDWFRQWDLQVDOLVWRIYDOXHVWRDGGHLWKHUWKURXJKKDUGFRGHGYDOXHVRU
KRVWODQJXDJHYDULDEOHV
g $6(/(&7VWDWHPHQWWKDWUHWULHYHVYDOXHVIURPRQHWDEOHWRDGGWRDQRWKHU
7KHV\QWD[RI,16(57LVDVIROORZV
INSERT [TRANSACTION name] INTO table [(col [, col ...])]
{VALUES (<val>[:ind] [, <val>[:ind] ...])
| SELECT <clause>};

7KHOLVWRIFROXPQVLQWRZKLFKWRLQVHUWYDOXHVLVRSWLRQDOLQ'64/DSSOLFDWLRQV,ILWLV
RPLWWHGWKHQYDOXHVDUHLQVHUWHGLQWRDWDEOH·VFROXPQVDFFRUGLQJWRWKHRUGHULQZKLFKWKH
FROXPQVZHUHFUHDWHG,IWKHUHDUHPRUHFROXPQVWKDQYDOXHVWKHUHPDLQLQJFROXPQVDUH
ILOOHGZLWK]HURV

Using VALUES to insert columns


8VHWKH9$/8(6FODXVHWRDGGDURZRIVSHFLILFYDOXHVWRDWDEOHRUWRDGGYDOXHVHQWHUHGE\
DXVHUDWUXQWLPH7KHOLVWRIYDOXHVWKDWIROORZVWKHNH\ZRUGFDQFRPHIURPHLWKHUIURP
KRVWODQJXDJHYDULDEOHVRUIURPKDUGFRGHGDVVLJQPHQWV
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWDGGVDQHZURZWRWKH'(3$570(17WDEOHXVLQJ
KDUGFRGHGYDOXHDVVLJQPHQWV
EXEC SQL
INSERT INTO DEPARTMENT (DEPT_NO, DEPARTMENT)
VALUES (7734, "Marketing");

%HFDXVHWKH'(3$570(17WDEOHFRQWDLQVDGGLWLRQDOFROXPQVQRWVSHFLILHGLQWKH,16(57
18//YDOXHVDUHDVVLJQHGWRWKHPLVVLQJILHOGV
7KHIROORZLQJ&FRGHH[DPSOHSURPSWVDXVHUIRULQIRUPDWLRQWRDGGWRWKH'(3$570(17
WDEOHDQGLQVHUWVWKRVHYDOXHVIURPKRVWYDULDEOHV
. . .
EXEC SQL
BEGIN DECLARE SECTION;
char department[26], dept_no[16];
int dept_num;

PROGRAMMER’S GUIDE 143


CHAPTER 6 WORKING WITH DATA

EXEC SQL
END DECLARE SECTION;
. . .
printf("Enter name of department: ");
gets(department);
printf("\nEnter department number: ");
dept_num = atoi(gets(dept_no));
EXEC SQL
INSERT INTO COUNTRIES (DEPT_NO, DEPARTMENT)
VALUES (:dept_num, :department);

:KHQKRVWYDULDEOHVDUHXVHGLQWKHYDOXHVOLVWWKH\PXVWEHSUHFHGHGE\FRORQV  VRWKDW
64/FDQGLVWLQJXLVKWKHPIURPWDEOHFROXPQQDPHV

Using SELECT to insert columns


7RLQVHUWYDOXHVIURPRQHWDEOHLQWRDQRWKHUURZLQWKHVDPHWDEOHRULQWRDURZLQDQRWKHU
WDEOHXVHD6(/(&7VWDWHPHQWWRVSHFLI\DOLVWRILQVHUWLRQYDOXHV)RUH[DPSOHWKHIROORZLQJ
,16(57VWDWHPHQWFRSLHV'(3$570(17DQG%8'*(7LQIRUPDWLRQDERXWWKHSXEOLFDWLRQV
GHSDUWPHQWIURPWKH2/''(37WDEOHWRWKH'(3$570(17WDEOH,WDOVRLOOXVWUDWHVKRZ
YDOXHVFDQEHKDUGFRGHGLQWRD6(/(&7VWDWHPHQWWRVXEVWLWXWHDFWXDOFROXPQGDWD
EXEC SQL
INSERT INTO DEPARTMENTS (DEPT_NO, DEPARTMENT, BUDGET)
SELECT DEPT_NO, "Publications", BUDGET
FROM OLDDEPT
WHERE DEPARTMENT = "Documentation";

7KHDVVLJQPHQWVLQWKH6(/(&7FDQLQFOXGHDULWKPHWLFRSHUDWLRQV)RUH[DPSOHVXSSRVHDQ
DSSOLFDWLRQNHHSVWUDFNRIHPSOR\HHVE\XVLQJDQHPSOR\HHQXPEHU:KHQDQHZHPSOR\HH
LVKLUHGWKHIROORZLQJVWDWHPHQWLQVHUWVDQHZHPSOR\HHURZLQWRWKH(03/2<((WDEOHDQG
DVVLJQVDQHZHPSOR\HHQXPEHUWRWKHURZE\XVLQJD6(/(&7VWDWHPHQWWRILQGWKHFXUUHQW
PD[LPXPHPSOR\HHQXPEHUDQGDGGLQJRQHWRLW,WDOVRUHDGVYDOXHVIRU/$67B1$0(DQG
),567B1$0(IURPWKHKRVWYDULDEOHVODVWQDPHDQGILUVWQDPH
EXEC SQL
INSERT INTO EMPLOYEE (EMP_NO, LAST_NAME, FIRST_NAME)
SELECT (MAX(EMP_NO) + 1, :lastname, :firstname)
FROM EMPLOYEE;

144 INTERBASE 5
INSERTING DATA

Inserting rows with NULL column values


6RPHWLPHVZKHQDQHZURZLVDGGHGWRDWDEOHYDOXHVDUHQRWQHFHVVDU\RUDYDLODEOHIRUDOO
LWVFROXPQV,QWKHVHFDVHVD18//YDOXHVKRXOGEHDVVLJQHGWRWKRVHFROXPQVZKHQWKHURZ
LVLQVHUWHG7KHUHDUHWKUHHZD\VWRDVVLJQD18//YDOXHWRDFROXPQRQLQVHUWLRQ
g ,JQRUHWKHFROXPQ
g $VVLJQD18//YDOXHWRWKHFROXPQ7KLVLVVWDQGDUG64/SUDFWLFH
g 8VHLQGLFDWRUYDULDEOHV

4 ,JQRULQJDFROXPQ
$18//YDOXHLVDVVLJQHGWRDQ\FROXPQWKDWLVQRWH[SOLFLWO\VSHFLILHGLQDQ,172FODXVH
:KHQ,QWHU%DVHHQFRXQWHUVDQXQUHIHUHQFHGFROXPQGXULQJLQVHUWLRQLWVHWVDIODJIRUWKH
FROXPQLQGLFDWLQJWKDWLWVYDOXHLVXQNQRZQ)RUH[DPSOHWKH'(3$570(17WDEOHFRQWDLQV
VHYHUDOFROXPQVDPRQJWKHP+($'B'(3701*5B12DQG%8'*(77KHIROORZLQJ
,16(57GRHVQRWSURYLGHYDOXHVIRUWKHVHFROXPQV
EXEC SQL
INSERT INTO DEPARTMENT (DEPT_NO, DEPARTMENT)
VALUES (:newdept_no, :newdept_name);

%HFDXVH+($'B'(3701*5B12DQG%8'*(7DUHQRWVSHFLILHG,QWHU%DVHVHWVWKH18//
YDOXHIODJIRUHDFKRIWKHVHFROXPQV
Note ,IDFROXPQLVDGGHGWRDQH[LVWLQJWDEOH,QWHU%DVHVHWVD18//YDOXHIODJIRUDOO
H[LVWLQJURZVLQWKHWDEOH

4 $VVLJQLQJD18//YDOXHWRDFROXPQ
:KHQDVSHFLILFYDOXHLVQRWSURYLGHGIRUDFROXPQRQLQVHUWLRQLWLVVWDQGDUG64/SUDFWLFH
WRDVVLJQD18//YDOXHWRWKDWFROXPQ,Q,QWHU%DVHDFROXPQLVVHWWR18//E\VSHFLI\LQJ
18//IRUWKHFROXPQLQWKH,16(57VWDWHPHQW
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVWRUHVDURZLQWRWKH'(3$570(17WDEOHDVVLJQVWKH
YDOXHVRIKRVWYDULDEOHVWRVRPHFROXPQVDQGDVVLJQVD18//YDOXHWRRWKHUFROXPQV
EXEC SQL
INSERT INTO DEPARTMENT
(DEPT_NO, DEPARTMENT, HEAD_DEPT, MNGR_NO, BUDGET,
LOCATION, PHONE_NO)
VALUES (:dept_no, :dept_name, NULL, NULL, 1500000, NULL, NULL);

PROGRAMMER’S GUIDE 145


CHAPTER 6 WORKING WITH DATA

4 8VLQJLQGLFDWRUYDULDEOHV
$QRWKHUPHWKRGIRUWUDSSLQJDQGDVVLJQLQJ18//YDOXHV³WKURXJKLQGLFDWRUYDULDEOHV³LV
QHFHVVDU\LQDSSOLFDWLRQVWKDWSURPSWXVHUVIRUGDWDZKHUHXVHUVFDQFKRRVHQRWWRHQWHU
YDOXHV%\GHIDXOWZKHQ,QWHU%DVHVWRUHVQHZGDWDLWVWRUHV]HURHVIRU18//QXPHULFGDWD
DQGVSDFHVIRU18//FKDUDFWHUGDWD%HFDXVH]HURHVDQGVSDFHVPD\EHYDOLGGDWDLWEHFRPHV
LPSRVVLEOHWRGLVWLQJXLVKPLVVLQJGDWDLQWKHQHZURZIURPDFWXDO]HURHVDQGVSDFHV
7RWUDSPLVVLQJGDWDZLWKLQGLFDWRUYDULDEOHVDQGVWRUH18//YDOXHIODJVIROORZWKHVHVWHSV
 'HFODUHDKRVWODQJXDJHYDULDEOHWRXVHDVDQLQGLFDWRUYDULDEOH
 7HVWDYDOXHHQWHUHGE\WKHXVHUDQGVHWWKHLQGLFDWRUYDULDEOHWRRQHRIWKH
IROORZLQJYDOXHV

0 The host-language variable contains data.


–1 The host-language variable does not contain data.

 $VVRFLDWHWKHLQGLFDWRUYDULDEOHZLWKWKHKRVWYDULDEOHLQWKH,16(57VWDWHPHQW
XVLQJWKHIROORZLQJV\QWD[
INSERT INTO table (<col> [, <col> ...])
VALUES (:variable [INDICATOR] :indicator
[, :variable [INDICATOR] :indicator ...]);
Note 7KH,1',&$725NH\ZRUGLVRSWLRQDO
)RUH[DPSOHWKHIROORZLQJ&FRGHIUDJPHQWSURPSWVWKHXVHUIRUWKHQDPHRIDGHSDUWPHQW
WKHGHSDUWPHQWQXPEHUDQGDEXGJHWIRUWKHGHSDUWPHQW,WWHVWVWKDWWKHXVHUKDVHQWHUHGD
EXGJHW,IQRWLWVHWVWKHLQGLFDWRUYDULDEOHELWR²2WKHUZLVHLWVHWVELWR)LQDOO\WKH
SURJUDP,16(576WKHLQIRUPDWLRQLQWRWKH'(3$570(17WDEOH,IWKHLQGLFDWRUYDULDEOHLV
²WKHQQRDFWXDOGDWDLVVWRUHGLQWKH%8'*(7FROXPQEXWDIODJLVVHWIRUWKHFROXPQ
LQGLFDWLQJWKDWWKHYDOXHLV18//
. . .
EXEC SQL
BEGIN DECLARE SECTION;
short bi; /* indicator variable declaration */
char department[26], dept_no_ascii[26], budget_ascii[26];
long num_val; /* host variable for inserting budget */
short dept_no;
EXEC SQL
END DECLARE SECTION;
. . .
printf("Enter new department name: ");
gets(cidepartment);

146 INTERBASE 5
INSERTING DATA

printf("\nEnter department number: ");


gets(dept_no_ascii);
printf("\nEnter department’s budget: ");
gets(budget_ascii);
if (budget_ascii = "")
{
bi = -1; num_val = 0;
}
else
{
bi = 0;
num_val = atoi(budget_ascii);
}
dept_no = atoi(dept_no_ascii);
EXEC SQL
INSERT INTO DEPARTMENT (DEPARTMENT, DEPT_NO, BUDGET)
VALUES (:department, :dept_no, :num_val INDICATOR :bi);
. . .

,QGLFDWRUVWDWXVFDQDOVREHGHWHUPLQHGIRUGDWDUHWULHYHGIURPDWDEOH)RULQIRUPDWLRQDERXW
WUDSSLQJ18//YDOXHVUHWULHYHGIURPDWDEOHVHH´5HWULHYLQJLQGLFDWRUVWDWXVµRQSDJH 

Inserting data through a view


1HZURZVFDQEHLQVHUWHGWKURXJKDYLHZLIWKHIROORZLQJFRQGLWLRQVDUHPHW
g 7KHYLHZLVXSGDWDEOH)RUDFRPSOHWHGLVFXVVLRQRIXSGDWDEOHYLHZVVHHWKH'DWD'HILQLWLRQ
*XLGH
g 7KHYLHZLVFUHDWHGXVLQJWKH:,7+&+(&.237,21
g $XVHURUVWRUHGSURFHGXUHKDV,16(57SULYLOHJHIRUWKHYLHZ
9DOXHVFDQRQO\EHLQVHUWHGWKURXJKDYLHZIRUWKRVHFROXPQVQDPHGLQWKHYLHZ,QWHU%DVH
VWRUHV18//YDOXHVIRUXQUHIHUHQFHGFROXPQV)RUH[DPSOHVXSSRVHWKHYLHZ3$57B'(37
LVGHILQHGDVIROORZV
EXEC SQL
CREATE VIEW PART_DEPT
(DEPARTMENT, DEPT_NO, BUDGET)
AS SELECT DEPARTMENT, DEPT_NO, BUDGET
FROM DEPARTMENT
WHERE DEPT_NO NOT NULL AND BUDGET > 50000
WITH CHECK OPTION;

PROGRAMMER’S GUIDE 147


CHAPTER 6 WORKING WITH DATA

%HFDXVH3$57B'(37UHIHUHQFHVDVLQJOHWDEOH'(3$570(17QHZGDWDFDQEHLQVHUWHGIRU
WKH'(3$570(17'(37B12DQG%8'*(7FROXPQV7KH:,7+&+(&.237,21DVVXUHV
WKDWDOOYDOXHVHQWHUHGWKURXJKWKHYLHZIDOOZLWKLQUDQJHVRIYDOXHVWKDWFDQEHVHOHFWHGE\
WKLVYLHZ)RUH[DPSOHWKHIROORZLQJVWDWHPHQWLQVHUWVDQHZURZIRUWKH3XEOLFDWLRQV
GHSDUWPHQWWKURXJKWKH3$57B'(37YLHZ
EXEC SQL
INSERT INTO PART_DEPT (DEPARTMENT, DEPT_NO, BUDGET)
VALUES ("Publications", "7735", 1500000);

,QWHU%DVHLQVHUWV18//YDOXHVIRUDOORWKHUFROXPQVLQWKH'(3$570(17WDEOHWKDWDUHQRW
DYDLODEOHGLUHFWO\WKURXJKWKHYLHZ
)RULQIRUPDWLRQDERXWFUHDWLQJDYLHZVHH&KDSWHU´:RUNLQJZLWK'DWD'HILQLWLRQ
6WDWHPHQWVµ)RUWKHFRPSOHWHV\QWD[RI&5($7(9,(:VHHWKH/DQJXDJH5HIHUHQFH
Note 6HHWKHFKDSWHURQWULJJHUVLQWKH'DWD'HILQLWLRQ*XLGHIRUWLSVRQXVLQJWULJJHUVWR
XSGDWHQRQXSGDWDEOHYLHZV

Specifying transaction names in an INSERT


,QWHU%DVHHQDEOHVDQ64/DSSOLFDWLRQWRUXQVLPXOWDQHRXVWUDQVDFWLRQVLI
g (DFKWUDQVDFWLRQLVILUVWQDPHGZLWKD6(775$16$&7,21VWDWHPHQW)RUDFRPSOHWH
GLVFXVVLRQRIWUDQVDFWLRQKDQGOLQJDQGQDPLQJVHH&KDSWHU´:RUNLQJZLWK7UDQVDFWLRQVµ
g (DFKGDWDPDQLSXODWLRQVWDWHPHQW 6(/(&7,16(5783'$7('(/(7('(&/$5(23(1
)(7&+DQG&/26( VSHFLILHVD75$16$&7,21FODXVHWKDWLGHQWLILHVWKHQDPHRIWKH
WUDQVDFWLRQXQGHUZKLFKLWRSHUDWHV
g 64/VWDWHPHQWVDUHQRWG\QDPLF '64/ '64/GRHVQRWVXSSRUWXVHUVSHFLILHGWUDQVDFWLRQ
QDPHV
:LWK,16(57WKH75$16$&7,21FODXVHLQWHUYHQHVEHWZHHQWKH,16(57NH\ZRUGDQGWKHOLVW
RIFROXPQVWRLQVHUWDVLQWKHIROORZLQJV\QWD[IUDJPHQW
INSERT TRANSACTION name INTO table (col [, col ...])

7KH75$16$&7,21FODXVHLVRSWLRQDOLQVLQJOHWUDQVDFWLRQSURJUDPV,WPXVWEHXVHGLQD
PXOWLWUDQVDFWLRQSURJUDPXQOHVVDVWDWHPHQWRSHUDWHVXQGHUFRQWURORIWKHGHIDXOW
WUDQVDFWLRQgds__trans)RUH[DPSOHWKHIROORZLQJ,16(57LVFRQWUROOHGE\WKHWUDQVDFWLRQ
7
EXEC SQL
INSERT TRANSACTION T1 INTO DEPARTMENT (DEPARTMENT, DEPT_NO, BUDGET)
VALUES (:deptname, :deptno, :budget INDICATOR :bi);

148 INTERBASE 5
UPDATING DATA

Updating data
7RFKDQJHYDOXHVIRUH[LVWLQJURZVRIGDWDLQDWDEOHXVHWKH83'$7(VWDWHPHQW7RXSGDWH
DWDEOHDXVHURUSURFHGXUHPXVWKDYH83'$7(SULYLOHJHIRULW7KHV\QWD[RI83'$7(LV
UPDATE [TRANSACTION name] table
SET col = <assignment> [, col = <assignment> ...]
WHERE <search_condition> | WHERE CURRENT OF cursorname;

83'$7(FKDQJHVYDOXHVIRUFROXPQVVSHFLILHGLQWKH6(7FODXVHFROXPQVQRWOLVWHGLQWKH
6(7FODXVHDUHQRWFKDQJHG$VLQJOH83'$7(VWDWHPHQWFDQEHXVHGWRPRGLI\DQ\QXPEHU
RIURZVLQDWDEOH)RUH[DPSOHWKHIROORZLQJVWDWHPHQWPRGLILHVDVLQJOHURZ
EXEC SQL
UPDATE DEPARTMENT
SET DEPARTMENT = "Publications"
WHERE DEPARTMENT = "Documentation";

7KH:+(5(FODXVHLQWKLVH[DPSOHWDUJHWVDVLQJOHURZIRUXSGDWH,IWKHVDPHFKDQJHVKRXOG
EHSURSDJDWHGWRDQXPEHURIURZVLQDWDEOHWKH:+(5(FODXVHFDQEHPRUHJHQHUDO)RU
H[DPSOHWRFKDQJHDOORFFXUUHQFHVRI´'RFXPHQWDWLRQµWR´3XEOLFDWLRQVµIRUDOO
GHSDUWPHQWVLQWKH'(3$570(17WDEOHZKHUH'(3$570(17HTXDOV´'RFXPHQWDWLRQµWKH
83'$7(VWDWHPHQWZRXOGEHDVIROORZV
EXEC SQL
UPDATE DEPARTMENT
SET DEPARTMENT = "Publications"
WHERE DEPARTMENT = "Documentation";

8VLQJ83'$7(WRPDNHWKHVDPHPRGLILFDWLRQWRDQXPEHURIURZVLVVRPHWLPHVFDOOHGD
PDVVXSGDWHRUDVHDUFKHGXSGDWH
7KH:+(5(FODXVHLQDQ83'$7(VWDWHPHQWFDQFRQWDLQDVXETXHU\WKDWUHIHUHQFHVRQHRU
PRUHRWKHUWDEOHV)RUDFRPSOHWHGLVFXVVLRQRIVXETXHULHVVHH´8VLQJVXETXHULHVµRQ
SDJH 

Updating multiple rows


7KHUHDUHWZREDVLFPHWKRGVIRUPRGLI\LQJURZV
g 7KHVHDUFKHGXSGDWHPHWKRGZKHUHWKHVDPHFKDQJHVDUHDSSOLHGWRDQXPEHURIURZVLVPRVW
XVHIXOIRUDXWRPDWHGXSGDWLQJRIURZVZLWKRXWDFXUVRU
g 7KHSRVLWLRQHGXSGDWHPHWKRGZKHUHURZVDUHUHWULHYHGWKURXJKDFXUVRUDQGXSGDWHGURZE\
URZLVPRVWXVHIXOIRUHQDEOLQJXVHUVWRHQWHUGLIIHUHQWFKDQJHVIRUHDFKURZUHWULHYHG

PROGRAMMER’S GUIDE 149


CHAPTER 6 WORKING WITH DATA

$VHDUFKHGXSGDWHLVHDVLHUWRSURJUDPWKDQDSRVLWLRQHGXSGDWHEXWDOVRPRUHOLPLWHGLQ
ZKDWLWFDQDFFRPSOLVK

4 8VLQJDVHDUFKHGXSGDWH
8VHDVHDUFKHGXSGDWHWRPDNHWKHVDPHFKDQJHVWRDQXPEHURIURZV7KH83'$7(6(7
FODXVHVSHFLILHVWKHDFWXDOFKDQJHVWKDWDUHWREHPDGHWRFROXPQVIRUHDFKURZWKDWPDWFKHV
WKHVHDUFKFRQGLWLRQVSHFLILHGLQWKH:+(5(FODXVH9DOXHVWRVHWFDQEHVSHFLILHGDV
FRQVWDQWVRUYDULDEOHV
)RUH[DPSOHWKHIROORZLQJ&FRGHIUDJPHQWSURPSWVIRUDFRXQWU\QDPHDQGDSHUFHQWDJH
FKDQJHLQSRSXODWLRQWKHQXSGDWHVDOOFLWLHVLQWKDWFRXQWU\ZLWKWKHQHZSRSXODWLRQ
. . .
EXEC SQL
BEGIN DECLARE SECTION;
char country[26], asciimult[10];
int multiplier;
EXEC SQL
END DECLARE SECTION;
. . .
main ()
{
printf("Enter country with city populations needing adjustment: ");
gets(country);
printf("\nPercent change (100%% to -100%%:");
gets(asciimult);
multiplier = atoi(asciimult);
EXEC SQL
UPDATE CITIES
SET POPULATION = POPULATION * (1 + :multiplier / 100)
WHERE COUNTRY = :country;

if (SQLCODE && (SQLCODE != 100))


{
isc_print_sqlerr(SQLCODE, isc_status);
EXEC SQL
ROLLBACK RELEASE;
}
else
{
EXEC SQL
COMMIT RELEASE;
}
}

150 INTERBASE 5
UPDATING DATA

,03257$17 6HDUFKHGXSGDWHVFDQQRWEHSHUIRUPHGRQDUUD\VRIGDWDW\SHV

4 8VLQJDSRVLWLRQHGXSGDWH
8VHFXUVRUVWRVHOHFWURZVIRUXSGDWHZKHQSURPSWLQJXVHUVIRUFKDQJHVRQDURZE\URZ
EDVLVDQGGLVSOD\LQJSUHRUSRVWPRGLILFDWLRQYDOXHVEHWZHHQURZXSGDWHV8SGDWLQJ
WKURXJKDFXUVRULVDVHYHQVWHSSURFHVV
 'HFODUHKRVWODQJXDJHYDULDEOHVQHHGHGIRUWKHXSGDWHRSHUDWLRQ
 'HFODUHDFXUVRUGHVFULELQJWKHURZVWRUHWULHYHIRUXSGDWHDQGLQFOXGHWKH)25
83'$7(FODXVHLQ'64/)RUPRUHLQIRUPDWLRQDERXWGHFODULQJDQGXVLQJ
FXUVRUVVHH´6HOHFWLQJPXOWLSOHURZVµRQSDJH 
 2SHQWKHFXUVRU
 )HWFKDURZ
 'LVSOD\FXUUHQWYDOXHVDQGSURPSWIRUQHZYDOXHV
 8SGDWHWKHFXUUHQWO\VHOHFWHGURZXVLQJWKH:+(5(&855(172)FODXVH
 5HSHDWVWHSVWRXQWLODOOVHOHFWHGURZVDUHXSGDWHG
)RUH[DPSOHWKHIROORZLQJ&FRGHIUDJPHQWXSGDWHVWKH3238/$7,21FROXPQE\
XVHUVSHFLILHGDPRXQWVIRUFLWLHVLQWKH&,7,(6WDEOHWKDWDUHLQDFRXQWU\DOVRVSHFLILHGE\WKH
XVHU
. . .
EXEC SQL
BEGIN DECLARE SECTION;
char country[26], asciimult[10];
int multiplier;
EXEC SQL
END DECLARE SECTION;
. . .
main ()
{
EXEC SQL
DECLARE CHANGEPOP CURSOR FOR
SELECT CITY, POPULATION
FROM CITIES
WHERE COUNTRY = :country;

printf("Enter country with city populations needing adjustment: ");


gets(country);
EXEC SQL
OPEN CHANGEPOP;

PROGRAMMER’S GUIDE 151


CHAPTER 6 WORKING WITH DATA

EXEC SQL
FETCH CHANGEPOP INTO :country;
while(!SQLCODE)
{
printf("\nPercent change (100%% to -100%%:");
gets(asciimult);
multiplier = atoi(asciimult);
EXEC SQL
UPDATE CITIES
SET POPULATION = POPULATION * (1 + :multiplier / 100)
WHERE CURRENT OF CHANGEPOP;
EXEC SQL
FETCH CHANGEPOP INTO :country;
if (SQLCODE && (SQLCODE != 100))
{
isc_print_sqlerr(SQLCODE, isc_status);
EXEC SQL
ROLLBACK RELEASE;
exit(1);
}
}
EXEC SQL
COMMIT RELEASE;
}

,03257$17 8VLQJ)2583'$7(ZLWKDFXUVRUFDXVHVURZVWREHIHWFKHGIURPWKHGDWDEDVHRQHDWD
WLPH,I)2583'$7(LVRPLWWHGURZVDUHIHWFKHGLQEDWFKHV

NULLing columns with UPDATE


7RVHWDFROXPQ·VYDOXHWR18//GXULQJXSGDWHVSHFLI\D18//YDOXHIRUWKHFROXPQLQWKH
6(7FODXVH)RUH[DPSOHWKHIROORZLQJ83'$7(VHWVWKHEXGJHWRIDOOGHSDUWPHQWVZLWKRXW
PDQDJHUVWR18//
EXEC SQL
UPDATE DEPARTMENT
SET BUDGET = NULL
WHERE MNGR_NO = NULL;

152 INTERBASE 5
UPDATING DATA

Updating through a view


([LVWLQJURZVFDQEHXSGDWHGWKURXJKDYLHZLIWKHIROORZLQJFRQGLWLRQVDUHPHW
g 7KHYLHZLVXSGDWDEOH)RUDFRPSOHWHGLVFXVVLRQRIXSGDWDEOHYLHZVVHHWKH'DWD'HILQLWLRQ
*XLGH
g 7KHYLHZLVFUHDWHGXVLQJWKH:,7+&+(&.237,21
g $XVHURUVWRUHGSURFHGXUHKDV83'$7(SULYLOHJHIRUWKHYLHZ
9DOXHVFDQRQO\EHXSGDWHGWKURXJKDYLHZIRUWKRVHFROXPQVQDPHGLQWKHYLHZ)RU
H[DPSOHVXSSRVHWKHYLHZ3$57B'(37LVGHILQHGDVIROORZV
EXEC SQL
CREATE VIEW PART_DEPT
(DEPARTMENT, NUMBER, BUDGET)
AS SELECT DEPARTMENT, DEPT_NO, BUDGET
FROM DEPARTMENT
WITH CHECK OPTION;

%HFDXVH3$57B'(37UHIHUHQFHVDVLQJOHWDEOHGDWDFDQEHXSGDWHGIRUWKHFROXPQVQDPHG
LQWKHYLHZ7KH:,7+&+(&.237,21DVVXUHVWKDWDOOYDOXHVHQWHUHGWKURXJKWKHYLHZIDOO
ZLWKLQUDQJHVSUHVFULEHGIRUHDFKFROXPQZKHQWKH'(3$570(17WDEOHZDVFUHDWHG)RU
H[DPSOHWKHIROORZLQJVWDWHPHQWXSGDWHVWKHEXGJHWRIWKH3XEOLFDWLRQVGHSDUWPHQWWKURXJK
WKH3$57B'(37YLHZ
EXEC SQL
UPDATE PART_DEPT
SET BUDGET = 2505700
WHERE DEPARTMENT = "Publications";

)RULQIRUPDWLRQDERXWFUHDWLQJDYLHZVHH&KDSWHU´:RUNLQJZLWK'DWD'HILQLWLRQ
6WDWHPHQWVµ)RUWKHFRPSOHWHV\QWD[RI&5($7(9,(:VHHWKH/DQJXDJH5HIHUHQFH
Note 6HHWKHFKDSWHURQWULJJHUVLQWKH'DWD'HILQLWLRQ*XLGHIRUWLSVRQXVLQJWULJJHUVWR
XSGDWHQRQXSGDWDEOHYLHZV

Specifying transaction names in UPDATE


,QWHU%DVHHQDEOHVDQ64/DSSOLFDWLRQWRUXQVLPXOWDQHRXVWUDQVDFWLRQVLI
g (DFKWUDQVDFWLRQLVILUVWQDPHGZLWKD6(775$16$&7,21VWDWHPHQW)RUDFRPSOHWH
GLVFXVVLRQRIWUDQVDFWLRQKDQGOLQJDQGQDPLQJVHH&KDSWHU´:RUNLQJZLWK7UDQVDFWLRQVµ

PROGRAMMER’S GUIDE 153


CHAPTER 6 WORKING WITH DATA

g (DFKGDWDPDQLSXODWLRQVWDWHPHQW 6(/(&7,16(5783'$7('(/(7('(&/$5(23(1
)(7&+DQG&/26( VSHFLILHVD75$16$&7,21FODXVHWKDWLGHQWLILHVWKHQDPHRIWKH
WUDQVDFWLRQXQGHUZKLFKLWRSHUDWHV
g 64/VWDWHPHQWVDUHQRWG\QDPLF '64/ '64/GRHVQRWVXSSRUWPXOWLSOHVLPXOWDQHRXV
WUDQVDFWLRQV
,Q83'$7(WKH75$16$&7,21FODXVHLQWHUYHQHVEHWZHHQWKH83'$7(NH\ZRUGDQGWKH
QDPHRIWKHWDEOHWRXSGDWHDVLQWKHIROORZLQJV\QWD[
UPDATE [TRANSACTION name] table
SET col = <assignment> [, col = <assignment> ...]
WHERE <search_condition> | WHERE CURRENT OF cursorname;

7KH75$16$&7,21FODXVHPXVWEHXVHGLQPXOWLWUDQVDFWLRQSURJUDPVEXWLVRSWLRQDOLQ
VLQJOHWUDQVDFWLRQSURJUDPVRULQSURJUDPVZKHUHRQO\RQHWUDQVDFWLRQLVRSHQDWDWLPH)RU
H[DPSOHWKHIROORZLQJ83'$7(LVFRQWUROOHGE\WKHWUDQVDFWLRQ7
EXEC SQL
UPDATE TRANSACTION T1 DEPARTMENT
SET BUDGET = 2505700
WHERE DEPARTMENT = "Publications";

Deleting data
7RUHPRYHURZVRIGDWDIURPDWDEOHXVHWKH'(/(7(VWDWHPHQW7RGHOHWHURZVDXVHURU
SURFHGXUHPXVWKDYH'(/(7(SULYLOHJHIRUWKHWDEOH
7KHV\QWD[RI'(/(7(LV
DELETE [TRANSACTION name] FROM table
WHERE <search_condition> | WHERE CURRENT OF cursorname;

'(/(7(LUUHWULHYDEO\UHPRYHVHQWLUHURZVIURPWKHWDEOHVSHFLILHGLQWKH)520FODXVH
UHJDUGOHVVRIHDFKFROXPQ·VGDWDW\SH
$VLQJOH'(/(7(FDQEHXVHGWRUHPRYHDQ\QXPEHURIURZVLQDWDEOH)RUH[DPSOHWKH
IROORZLQJVWDWHPHQWUHPRYHVWKHVLQJOHURZFRQWDLQLQJ´&KDQQHO0DUNHWLQJµIURPWKH
'(3$570(17WDEOH
EXEC SQL
DELETE FROM DEPARTMENT
WHERE DEPARTMENT = "Channel Marketing:;

154 INTERBASE 5
DELETING DATA

7KH:+(5(FODXVHLQWKLVH[DPSOHWDUJHWVDVLQJOHURZIRUXSGDWH,IWKHVDPHGHOHWLRQ
FULWHULDDSSO\WRDQXPEHURIURZVLQDWDEOHWKH:+(5(FODXVHFDQEHPRUHJHQHUDO)RU
H[DPSOHWRUHPRYHDOOURZVIURPWKH'(3$570(17WDEOHZLWK%8'*(7YDOXHV
 WKH'(/(7(VWDWHPHQWZRXOGEHDVIROORZV
EXEC SQL
DELETE FROM DEPARTMENT
WHERE BUDGET < 1000000;

8VLQJ'(/(7(WRUHPRYHDQXPEHURIURZVLVVRPHWLPHVFDOOHGDPDVVGHOHWH
7KH:+(5(FODXVHLQD'(/(7(VWDWHPHQWFDQFRQWDLQDVXETXHU\WKDWUHIHUHQFHVRQHRU
PRUHRWKHUWDEOHV)RUDGLVFXVVLRQRIVXETXHULHVVHH´8VLQJVXETXHULHVµRQSDJH 

Deleting multiple rows


7KHUHDUHWZRPHWKRGVIRUPRGLI\LQJURZV
g 7KHVHDUFKHGGHOHWHPHWKRGZKHUHWKHVDPHGHOHWLRQFRQGLWLRQDSSOLHVWRDQXPEHURIURZVLV
PRVWXVHIXOIRUDXWRPDWHGUHPRYDORIURZV
g 7KHSRVLWLRQHGGHOHWHPHWKRGZKHUHURZVDUHUHWULHYHGWKURXJKDFXUVRUDQGGHOHWHGURZE\
URZLVPRVWXVHIXOIRUHQDEOLQJXVHUVWRFKRRVHZKLFKURZVWKDWPHHWFHUWDLQFRQGLWLRQV
VKRXOGEHUHPRYHG
$VHDUFKHGGHOHWHLVHDVLHUWRSURJUDPWKDQDSRVLWLRQHGGHOHWHEXWOHVVIOH[LEOH

4 8VLQJDVHDUFKHGGHOHWH
8VHDVHDUFKHGGHOHWHWRUHPRYHDQXPEHURIURZVWKDWPDWFKDFRQGLWLRQVSHFLILHGLQWKH
:+(5(FODXVH)RUH[DPSOHWKHIROORZLQJ&FRGHIUDJPHQWSURPSWVIRUDFRXQWU\QDPH
WKHQGHOHWHVDOOURZVWKDWKDYHFLWLHVLQWKDWFRXQWU\
. . .
EXEC SQL
BEGIN DECLARE SECTION;
char country[26];
EXEC SQL
END DECLARE SECTION;
. . .
main ()
{
printf("Enter country with cities to delete: ");
gets(country);
EXEC SQL
DELETE FROM CITIES

PROGRAMMER’S GUIDE 155


CHAPTER 6 WORKING WITH DATA

WHERE COUNTRY = :country;

if(SQLCODE && (SQLCODE != 100))


{
isc_print_sqlerr(SQLCODE, isc_status);
EXEC SQL
ROLLBACK RELEASE;
}
else
{
EXEC SQL
COMMIT RELEASE;
}
}

4 8VLQJDSRVLWLRQHGGHOHWH
8VHFXUVRUVWRVHOHFWURZVIRUGHOHWLRQZKHQXVHUVVKRXOGGHFLGHGHOHWLRQRQDURZE\URZ
EDVLVDQGGLVSOD\LQJSUHRUSRVWPRGLILFDWLRQYDOXHVEHWZHHQURZXSGDWHV8SGDWLQJ
WKURXJKDFXUVRULVDVHYHQVWHSSURFHVV
 'HFODUHKRVWODQJXDJHYDULDEOHVQHHGHGIRUWKHGHOHWHRSHUDWLRQ
 'HFODUHDFXUVRUGHVFULELQJWKHURZVWRUHWULHYHIRUSRVVLEOHGHOHWLRQDQG
LQFOXGHWKH)2583'$7(FODXVH)RUPRUHLQIRUPDWLRQDERXWGHFODULQJDQG
XVLQJFXUVRUVVHH´6HOHFWLQJPXOWLSOHURZVµRQSDJH 
 2SHQWKHFXUVRU
 )HWFKDURZ
 'LVSOD\FXUUHQWYDOXHVDQGSURPSWIRUSHUPLVVLRQWRGHOHWH
 'HOHWHWKHFXUUHQWO\VHOHFWHGURZXVLQJWKH:+(5(&855(172)FODXVHWR
VSHFLI\WKHQDPHRIWKHFXUVRU
 5HSHDWVWHSVWRXQWLODOOVHOHFWHGURZVDUHGHOHWHG
)RUH[DPSOHWKHIROORZLQJ&FRGHGHOHWHVURZVLQWKH&,7,(6WDEOHWKDWDUHLQ1RUWK$PHULFD
RQO\LIDXVHUW\SHVYZKHQSURPSWHG
. . .
EXEC SQL
BEGIN DECLARE SECTION;
char cityname[26];
EXEC SQL
END DECLARE SECTION;
char response[5];
. . .

156 INTERBASE 5
DELETING DATA

main ()
{
EXEC SQL
DECLARE DELETECITY CURSOR FOR
SELECT CITY,
FROM CITIES
WHERE CONTINENT = "North America";
EXEC SQL
OPEN DELETECITY;
while (!SQLCODE)
{
EXEC SQL
FETCH DELETECITY INTO :cityname;
if (SQLCODE)
{
if (SQLCODE == 100)
{
printf("Deletions complete.");
EXEC SQL
COMMIT;
EXEC SQL
CLOSE DELETECITY;
EXEC SQL
DISCONNECT ALL:
}
isc_print_sqlerr(SQLCODE, isc_status);
EXEC SQL
ROLLBACK;
EXEC SQL
DISCONNECT ALL;
exit(1);
}
printf("\nDelete %s (Y/N)?", cityname);
gets(response);
if(response[0] == ’Y’ || response == ’y’)
{
EXEC SQL
DELETE FROM CITIES
WHERE CURRENT OF DELETECITY;
if(SQLCODE && (SQLCODE != 100))
{
isc_print_sqlerr(SQLCODE, isc_status);
EXEC SQL
ROLLBACK;

PROGRAMMER’S GUIDE 157


CHAPTER 6 WORKING WITH DATA

EXEC SQL
DISCONNECT;
exit(1);
}
}
}

Deleting through a view


(QWLUHURZVFDQEHGHOHWHGWKURXJKDYLHZLIWKHIROORZLQJFRQGLWLRQVDUHPHW
g 7KHYLHZLVXSGDWDEOH)RUDFRPSOHWHGLVFXVVLRQRIXSGDWDEOHYLHZVVHHWKH'DWD'HILQLWLRQ
*XLGH
g $XVHURUVWRUHGSURFHGXUHKDV'(/(7(SULYLOHJHIRUWKHYLHZ
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWGHOHWHVDOOGHSDUWPHQWVZLWKEXGJHWVXQGHU
IURPWKH'(3$570(17WDEOHWKURXJKWKH3$57B'(37YLHZ
EXEC SQL
DELETE FROM PART_DEPT
WHERE BUDGET < 1000000;

)RULQIRUPDWLRQDERXWFUHDWLQJDYLHZVHH&KDSWHU´:RUNLQJZLWK'DWD'HILQLWLRQ
6WDWHPHQWVµ)RU&5($7(9,(:V\QWD[VHHWKH/DQJXDJH5HIHUHQFH
Note 6HHWKHFKDSWHURQWULJJHUVLQWKH'DWD'HILQLWLRQ*XLGHIRUWLSVRQXVLQJWULJJHUVWR
GHOHWHWKURXJKQRQXSGDWDEOHYLHZV

Specifying transaction names in a DELETE


,QWHU%DVHHQDEOHVDQ64/DSSOLFDWLRQWRUXQVLPXOWDQHRXVWUDQVDFWLRQVLI
g (DFKWUDQVDFWLRQLVILUVWQDPHGZLWKD6(775$16$&7,21VWDWHPHQW)RUDFRPSOHWH
GLVFXVVLRQRIWUDQVDFWLRQKDQGOLQJDQGQDPLQJVHH&KDSWHU´:RUNLQJZLWK7UDQVDFWLRQVµ
g (DFKGDWDPDQLSXODWLRQVWDWHPHQW 6(/(&7,16(5783'$7('(/(7('(&/$5(23(1
)(7&+DQG&/26( VSHFLILHVD75$16$&7,21FODXVHWKDWLGHQWLILHVWKHQDPHRIWKH
WUDQVDFWLRQXQGHUZKLFKLWRSHUDWHV
g 64/VWDWHPHQWVDUHQRWG\QDPLF '64/ '64/GRHVQRWVXSSRUWPXOWLSOHVLPXOWDQHRXV
WUDQVDFWLRQV

158 INTERBASE 5
DELETING DATA

)RU'(/(7(WKH75$16$&7,21FODXVHLQWHUYHQHVEHWZHHQWKH'(/(7(NH\ZRUGDQGWKH
)520FODXVHVSHFLI\LQJWKHWDEOHIURPZKLFKWRGHOHWH
DELETE TRANSACTION name FROM table ...

7KH75$16$&7,21FODXVHLVRSWLRQDOLQVLQJOHWUDQVDFWLRQSURJUDPVRULQSURJUDPVZKHUH
RQO\RQHWUDQVDFWLRQLVRSHQDWDWLPH,WPXVWEHXVHGLQDPXOWLWUDQVDFWLRQSURJUDP)RU
H[DPSOHWKHIROORZLQJ'(/(7(LVFRQWUROOHGE\WKHWUDQVDFWLRQ7
EXEC SQL
DELETE TRANSACTION T1 FROM PART_DEPT
WHERE BUDGET < 1000000";

PROGRAMMER’S GUIDE 159


CHAPTER

Working with Dates


Chapter7
7
0RVWKRVWODQJXDJHVGRQRWVXSSRUWWKH'$7(GDWDW\SH,QVWHDGWKH\WUHDWGDWHVDVVWULQJV
RUVWUXFWXUHV,QWHU%DVHVXSSRUWVD'$7(GDWDW\SHWKDWLVVWRUHGLQWDEOHVDVWZRORQJLQWHJHUV
$Q,QWHU%DVH'$7(GDWDW\SHLQFOXGHVLQIRUPDWLRQDERXW\HDUPRQWKGD\RIWKHPRQWKDQG
WLPH
7KLVFKDSWHUGLVFXVVHVKRZWR6(/(&7,16(57DQG83'$7(GDWHVIURPWDEOHVLQ64/
DSSOLFDWLRQVXVLQJWKHIROORZLQJLVFFDOOLQWHUIDFHURXWLQHV
g isc_decode_date()WRFRQYHUWWKH,QWHU%DVHLQWHUQDOGDWHIRUPDWWRWKH&WLPHVWUXFWXUH
g isc_encode_date()WRFRQYHUWWKH&WLPHVWUXFWXUHWRWKHLQWHUQDO,QWHU%DVHGDWHIRUPDW
7KHFKDSWHUDOVRGLVFXVVHVKRZWRXVHWKH&$67 IXQFWLRQWRWUDQVODWHD'$7(GDWDW\SHLQWR
D&+$5$&7(5GDWDW\SHDQGEDFNDJDLQDQGKRZWRXVHWKH'$7(OLWHUDOV12:DQG72'$<
ZKHQVHOHFWLQJDQGLQVHUWLQJGDWHV
Note ,QWHU%DVHGRHVQRWGLUHFWO\VXSSRUW64/'$7(7,0(DQG7,0(67$03GDWDW\SHV

161
CHAPTER 7 WORKING WITH DATES

Selecting dates
7RVHOHFWDGDWHIURPDWDEOHDQGFRQYHUWLWWRDIRUPXVDEOHLQD&ODQJXDJHSURJUDPIROORZ
WKHVHVWHSV
 &UHDWHDKRVWYDULDEOHIRUD&WLPHVWUXFWXUH0RVW&DQG&FRPSLOHUVSURYLGH
DW\SHGHIGHFODUDWLRQWPIRUWKH&WLPHVWUXFWXUHLQWKHWLPHKKHDGHUILOH7KH
IROORZLQJ&FRGHLQFOXGHVWKDWKHDGHUILOHDQGGHFODUHVDYDULDEOHRIW\SHWP
#include <time.h>;
. . .
struct tm hire_time;
. . .

7RFUHDWHKRVWODQJXDJHWLPHVWUXFWXUHVLQODQJXDJHVRWKHUWKDQ&DQG&VHHWKH
KRVWODQJXDJHUHIHUHQFHPDQXDO
 &UHDWHDKRVWYDULDEOHRIW\SH,6&B48$')RUH[DPSOHWKHKRVWYDULDEOH
GHFODUDWLRQPLJKWORRNOLNHWKLV
ISC_QUAD hire_date;

7KH,6&B48$'VWUXFWXUHLVDXWRPDWLFDOO\GHFODUHGIRUSURJUDPVZKHQWKH\DUH
SUHSURFHVVHGZLWKgpreEXWWKHSURJUDPPHUPXVWGHFODUHDFWXDOKRVWODQJXDJHYDULDEOHV
RIW\SH,6&B48$'
 5HWULHYHDGDWHIURPDWDEOHLQWRWKH,6&B48$'YDULDEOH)RUH[DPSOH
EXEC SQL
SELECT LAST_NAME, FIRST_NAME, DATE_OF_HIRE
INTO :lname, :fname, :hire_date
FROM EMPLOYEE
WHERE LAST_NAME = ’Smith’ AND FIRST_NAME = ’Margaret’;

&RQYHUWWKH,6&B48$'YDULDEOHLQWRDQXPHULF8QL[IRUPDWZLWKWKH,QWHU%DVHIXQFWLRQ
isc_decode_date()7KLVIXQFWLRQLVDXWRPDWLFDOO\GHFODUHGIRUSURJUDPVZKHQWKH\DUH
SUHSURFHVVHGZLWKgpreisc_decode_date()UHTXLUHVWZRSDUDPHWHUVWKHDGGUHVVRIWKH
,6&B48$'KRVWODQJXDJHYDULDEOHDQGWKHDGGUHVVRIWKHWPKRVWODQJXDJHYDULDEOH)RU
H[DPSOHWKHIROORZLQJFRGHIUDJPHQWFRYHUWVKLUHBGDWHWRKLUHBWLPH
isc_decode_date(&hire_date, &hire_time);

162 INTERBASE 5
INSERTING DATES

Inserting dates
7RLQVHUWDGDWHLQDWDEOHLWPXVWEHFRQYHUWHGIURPWKHKRVWODQJXDJHIRUPDWLQWR,QWHU%DVH
IRUPDWDQGWKHQVWRUHG7RSHUIRUPWKHFRQYHUVLRQDQGLQVHUWLRQLQD&SURJUDPIROORZ
WKHVHVWHSV
 &UHDWHDKRVWYDULDEOHIRUD&WLPHVWUXFWXUH0RVW&DQG&FRPSLOHUVSURYLGH
DW\SHGHIGHFODUDWLRQWPIRUWKH&WLPHVWUXFWXUHLQWKHWLPHKKHDGHUILOH7KH
IROORZLQJ&FRGHLQFOXGHVWKDWKHDGHUILOHDQGGHFODUHVDWPYDULDEOHKLUHBWLPH
#include <time.h>;
. . .
struct tm hire_time;
. . .

7RFUHDWHKRVWODQJXDJHWLPHVWUXFWXUHVLQODQJXDJHVRWKHUWKDQ&DQG&VHHWKH
KRVWODQJXDJHUHIHUHQFHPDQXDO
 &UHDWHDKRVWYDULDEOHRIW\SH,6&B48$'IRUXVHE\,QWHU%DVH)RUH[DPSOHWKH
KRVWYDULDEOHGHFODUDWLRQPLJKWORRNOLNHWKLV
ISC_QUAD mydate;

7KH,6&B48$'VWUXFWXUHLVDXWRPDWLFDOO\GHFODUHGIRUSURJUDPVZKHQWKH\DUH
SUHSURFHVVHGZLWKgpreEXWWKHSURJUDPPHUPXVWGHFODUHDFWXDOKRVWODQJXDJHYDULDEOHV
RIW\SH,6&B48$'
 3XWGDWHDQGWLPHLQIRUPDWLRQLQWRKLUHBWLPH
 8VHWKH,QWHU%DVHisc_encode_date()IXQFWLRQWRFRQYHUWWKHLQIRUPDWLRQLQ
KLUHBWLPHLQWR,QWHU%DVHLQWHUQDOIRUPDWDQGVWRUHWKDWIRUPDWWHGLQIRUPDWLRQLQ
WKH,6&B48$'KRVWYDULDEOH KLUHBGDWHLQWKHH[DPSOH 7KLVIXQFWLRQLV
DXWRPDWLFDOO\GHFODUHGIRUSURJUDPVZKHQWKH\DUHSUHSURFHVVHGZLWKgpre
isc_encode_date()UHTXLUHVWZRSDUDPHWHUVWKHDGGUHVVRIWKH8QL[WLPH
VWUXFWXUHDQGWKHDGGUHVVRIWKH,6&B48$'KRVWODQJXDJHYDULDEOH
)RUH[DPSOHWKHIROORZLQJFRGHFRQYHUWVKLUHBWLPHWRKLUHBGDWH
isc_encode_date(&hire_time, &hire_date);

 ,QVHUWWKHGDWHLQWRDWDEOH)RUH[DPSOH
EXEC SQL
INSERT INTO EMPLOYEE (EMP_NO, DEPARTMENT, DATE_OF_HIRE)
VALUES (:emp_no, :deptname, :hire_date);

PROGRAMMER’S GUIDE 163


CHAPTER 7 WORKING WITH DATES

Updating dates
7RXSGDWHDGDWHLQDWDEOHLWPXVWEHFRQYHUWHGIURPWKHKRVWODQJXDJHIRUPDWLQWR
,QWHU%DVHIRUPDWDQGWKHQVWRUHG7RFRQYHUWDKRVWYDULDEOHLQWR,QWHU%DVHIRUPDWVHH
´,QVHUWLQJGDWHVµRQSDJH 7KHDFWXDOXSGDWHLVSHUIRUPHGXVLQJDQ83'$7(VWDWHPHQW
)RUH[DPSOH
EXEC SQL
UPDATE EMPLOYEE
SET DATE_OF_HIRE = :hire_date
WHERE DATE_OF_HIRE < ’1 JAN 1994’

Using CAST() to convert dates


7KHEXLOWLQ&$67 IXQFWLRQFDQEHXVHGLQ6(/(&7VWDWHPHQWVWRWUDQVODWHD'$7(GDWDW\SH
LQWRD&+$5$&7(5RU180(5,&GDWDW\SHRUWRWUDQVODWH&+$5$&7(5DQG180(5,&
GDWDW\SHVLQWR'$7(GDWDW\SHV7\SLFDOO\&$67 LVXVHGLQWKH:+(5(FODXVHWRFRPSDUH
GLIIHUHQWGDWDW\SHV7KHV\QWD[IRU&$67 LV
CAST (<value> AS <datatype>)

,QWKHIROORZLQJ:+(5(FODXVH&$67 LVWUDQVODWHVD&+$5GDWDW\SH,17(59,(:B'$7(WR
D'$7(GDWDW\SHWRFRPSDUHDJDLQVWD'$7(GDWDW\SH+,5(B'$7(
… WHERE HIRE_DATE = CAST(INTERVIEW_DATE AS DATE);

,QWKHQH[WH[DPSOH&$67 WUDQVODWHVD'$7(GDWDW\SHLQWRD&+$5GDWDW\SH
… WHERE CAST(HIRE_DATE AS CHAR) = INTERVIEW_DATE;

&$67 DOVRFDQEHXVHGWRFRPSDUHFROXPQVZLWKGLIIHUHQWGDWDW\SHVLQWKHVDPHWDEOHRU
DFURVVWDEOHV

7,3 7RWUXQFDWHWKHWLPHSRUWLRQRIDGDWHILHOGFDVWWKHGDWHWRD&+$5WKDWLVORQJHQRXJKWR
FRQWDLQWKHGDWHEXWQRWWKHWLPH)RUH[DPSOH
CAST(INTERVIEW_DATE AS CHAR(7));

)RUPRUHLQIRUPDWLRQDERXW&$67 VHH&KDSWHU´:RUNLQJZLWK'DWDµ

164 INTERBASE 5
USING DATE LITERALS

Using date literals


,QWHU%DVHVXSSRUWVIRXUGDWHOLWHUDOV 12:  72'$<  <(67(5'$< DQG 7202552: 'DWH
OLWHUDOVDUHVWULQJYDOXHVHQWHUHGEHWZHHQTXRWDWLRQPDUNVWKDWFDQEHLQWHUSUHWHGDVGDWH
YDOXHVIRU6(/(&7,16(57DQG83'$7(RSHUDWLRQV 12: LVDGDWHOLWHUDOWKDWFRPELQHV
WRGD\·VGDWHDQGWLPHLQ,QWHU%DVHIRUPDW 72'$< LVWRGD\·VGDWHZLWKWLPHLQIRUPDWLRQVHW
WR]HUR6LPLODUO\ <(67(5'$< DQG 7202552: DUHWKHH[SHFWHGGDWHVZLWKWKHWLPH
LQIRUPDWLRQVHWWR]HUR
,Q6(/(&7 12: DQG 72'$< FDQEHXVHGLQWKHVHDUFKFRQGLWLRQRID:+(5(FODXVHWR
UHVWULFWWKHGDWDUHWULHYHG
EXEC SQL
SELECT * FROM CROSS_RATE WHERE UPDATE_DATE = ’TODAY’;

,Q,16(57DQG83'$7( 12: DQG 72'$< FDQEHXVHGWRHQWHUGDWHDQGWLPHYDOXHVLQVWHDG


RIUHO\LQJRQLVFFDOOVWRFRQYHUW&GDWHVWR,QWHU%DVHGDWHV
EXEC SQL
INSERT INTO CROSS_RATE VALUES(:from, :to, :rate, ’NOW’);
EXEC SQL
UPDATE CROSS_RATE
SET CONV_RATE = 1.75,
SET UPDATE_DATE = ’NOW’
WHERE FROM_CURRENCY = ’POUND’ AND TO_CURRENCT = ’DOLLAR’
AND UPDATE_DATE < ’TODAY’;

PROGRAMMER’S GUIDE 165


CHAPTER

Working with Blob Data


Chapter8
8
7KLVFKDSWHUGHVFULEHVWKH%/2%GDWDW\SHDQGLWVVXEW\SHVKRZWRVWRUH%OREVKRZWRDFFHVV
WKHPZLWK64/'64/DQG$3,FDOOVDQGKRZWRILOWHU%OREV,WDOVRLQFOXGHVLQIRUPDWLRQ
RQZULWLQJ%OREILOWHUV

What is a Blob?
$%ORELVDG\QDPLFDOO\VL]DEOHGDWDW\SHWKDWKDVQRVSHFLILHGVL]HDQGHQFRGLQJ<RXFDQXVH
D%OREWRVWRUHODUJHDPRXQWVRIGDWDRIYDULRXVW\SHVLQFOXGLQJ
g %LWPDSSHGLPDJHV
g 9HFWRUGUDZLQJV
g 6RXQGVYLGHRVHJPHQWVDQGRWKHUPXOWLPHGLDLQIRUPDWLRQ
g 7H[WDQGGDWDLQFOXGLQJERRNOHQJWKGRFXPHQWV
'DWDVWRUHGLQWKH%OREGDWDW\SHFDQEHPDQLSXODWHGLQPRVWRIWKHVDPHZD\VDVGDWDVWRUHG
LQDQ\RWKHUGDWDW\SH,QWHU%DVHVWRUHV%OREGDWDLQVLGHWKHGDWDEDVHLQFRQWUDVWWRVLPLODU
RWKHUV\VWHPVWKDWVWRUHSRLQWHUVWRQRQGDWDEDVHILOHV)RUHDFK%OREWKHUHLVDXQLTXH
LGHQWLILFDWLRQKDQGOHLQWKHDSSURSULDWHWDEOHWRSRLQWWRWKHGDWDEDVHORFDWLRQRIWKH%ORE
%\PDLQWDLQLQJWKH%OREGDWDZLWKLQWKHGDWDEDVH,QWHU%DVHLPSURYHVGDWDPDQDJHPHQWDQG
DFFHVV

167
CHAPTER 8 WORKING WITH BLOB DATA

7KHFRPELQDWLRQRIWUXHGDWDEDVHPDQDJHPHQWRI%OREGDWDDQGVXSSRUWIRUDYDULHW\RI
GDWDW\SHVPDNHV,QWHU%DVH%OREVXSSRUWLGHDOIRUWUDQVDFWLRQLQWHQVLYHPXOWLPHGLD
DSSOLFDWLRQV)RUH[DPSOH,QWHU%DVHLVDQH[FHOOHQWSODWIRUPIRULQWHUDFWLYHNLRVNDSSOLFDWLRQV
WKDWPLJKWSURYLGHKXQGUHGVRUWKRXVDQGVRISURGXFWGHVFULSWLRQVSKRWRJUDSKVDQGYLGHR
FOLSVLQDGGLWLRQWRSRLQWRIVDOHDQGRUGHUSURFHVVLQJFDSDELOLWLHV

How are Blob data stored?


%ORELVWKH,QWHU%DVHGDWDW\SHWKDWUHSUHVHQWVYDULRXVREMHFWVVXFKDVELWPDSSHGLPDJHV
VRXQGYLGHRDQGWH[W%HIRUH\RXVWRUHWKHVHLWHPVLQWKHGDWDEDVH\RXFUHDWHRUPDQDJH
WKHPDVSODWIRUPRUSURGXFWVSHFLILFILOHVRUGDWDVWUXFWXUHVVXFKDV
g 7,))3,&7%03:0)*(07$5*$RURWKHUELWPDSSHGRUYHFWRUJUDSKLFILOHV
g 0,',RU:$9VRXQGILOHV
g $XGLR9LGHR,QWHUOHDYHGIRUPDW $9, RU4XLFN7LPHYLGHRILOHV
g $6&,,0,)'2&57):3[RURWKHUWH[WILOHV
g &$'ILOHV
<RXPXVWORDGWKHVHILOHVIURPPHPRU\LQWRWKHGDWDEDVHSURJUDPPDWLFDOO\DV\RXGRDQ\
RWKHUKRVWODQJXDJHGDWDLWHPVRUUHFRUGV\RXLQWHQGWRVWRUHLQ,QWHU%DVH

168 INTERBASE 5
HOW ARE BLOB DATA STORED?

Blob subtypes
$OWKRXJK\RXPDQDJH%OREGDWDLQWKHVDPHZD\DVRWKHUGDWDW\SHV,QWHU%DVHSURYLGHVPRUH
IOH[LEOHGDWDW\SLQJUXOHVIRU%OREGDWD%HFDXVHWKHUHDUHPDQ\QDWLYHGDWDW\SHVWKDW\RXFDQ
GHILQHDV%OREGDWD,QWHU%DVHWUHDWVWKHPVRPHZKDWJHQHULFDOO\DQGDOORZV\RXWRGHILQH
\RXURZQGDWDW\SHNQRZQDVDVXEW\SH$OVR,QWHU%DVHSURYLGHVVHYHQVWDQGDUGVXEW\SHVZLWK
ZKLFK\RXFDQFKDUDFWHUL]H%OREGDWD

BLOB
subtype Description
0 Unstructured, generally applied to binary data or data of an indeterminate type
1 Text
2 Binary language representation (BLR)
3 Access control list
4 (Reserved for future use)
5 Encoded description of a table’s current metadata
6 Description of multi-database transaction that finished irregularly
TABLE 8.1 BLOB subtypes defined by InterBase

<RXFDQVSHFLI\XVHUGHILQHGVXEW\SHVDVQHJDWLYHQXPEHUVEHWZHHQ²DQG
²3RVLWLYHLQWHJHUVDUHUHVHUYHGIRU,QWHU%DVHVXEW\SHV
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWGHILQHVWKUHH%OREFROXPQV%OREZLWKVXEW\SH WKH
GHIDXOW %OREZLWKVXEW\SH 7(;7 DQG%OREZLWKXVHUGHILQHGVXEW\SH²
EXEC SQL CREATE TABLE TABLE2
(
BLOB1 BLOB,
BLOB2 BLOB SUB_TYPE 1,
BLOB3 BLOB SUB_TYPE -1
);

7RVSHFLI\ERWKDGHIDXOWVHJPHQWOHQJWKDQGDVXEW\SHZKHQFUHDWLQJD%OREFROXPQXVHWKH
6(*0(176,=(RSWLRQDIWHUWKH68%B7<3(RSWLRQ)RUH[DPSOH
EXEC SQL CREATE TABLE TABLE2
(
BLOB1 BLOB SUB_TYPE 1 SEGMENT SIZE 100;
);

PROGRAMMER’S GUIDE 169


CHAPTER 8 WORKING WITH BLOB DATA

7KHRQO\UXOH,QWHU%DVHHQIRUFHVRYHUWKHVHXVHUGHILQHGVXEW\SHVLVWKDWZKHQFRQYHUWLQJ
D%OREIURPRQHVXEW\SHWRDQRWKHUWKRVHVXEW\SHVPXVWEHFRPSDWLEOH,QWHU%DVHGRHVQRW
RWKHUZLVHHQIRUFHVXEW\SHLQWHJULW\

Blob database storage


%HFDXVH%OREGDWDDUHW\SLFDOO\ODUJHYDULDEO\VL]HGREMHFWVRIELQDU\RUWH[WGDWD,QWHU%DVH
VWRUHVWKHPPRVWHIILFLHQWO\XVLQJDPHWKRGRIVHJPHQWDWLRQ,WZRXOGEHDQLQHIILFLHQWXVH
RIGLVNVSDFHWRVWRUHHDFK%OREDVRQHFRQWLJXRXVPDVV,QVWHDG,QWHU%DVHVWRUHVHDFK%ORE
LQVHJPHQWVWKDWDUHLQGH[HGE\DKDQGOHWKDW,QWHU%DVHJHQHUDWHVZKHQ\RXFUHDWHWKH%ORE
7KLVKDQGOHLVNQRZQDVWKH%ORE,'DQGLVDTXDGZRUG ELW FRQWDLQLQJDXQLTXH
FRPELQDWLRQRIWDEOHLGHQWLILHUDQG%ORELGHQWLILHU
7KH%ORE,'IRUHDFK%ORELVVWRUHGLQLWVDSSURSULDWHILHOGLQWKHWDEOHUHFRUG7KH%ORE,'
SRLQWVWRWKHILUVWVHJPHQWRIWKH%ORERUWRDSDJHRISRLQWHUVHDFKRIZKLFKSRLQWVWRD
VHJPHQWRIRQHRUPRUH%OREILHOGV<RXFDQUHWULHYHWKH%ORE,'E\H[HFXWLQJD6(/(&7
VWDWHPHQWWKDWVSHFLILHVWKH%OREDVWKHWDUJHWDVLQWKHIROORZLQJH[DPSOH
EXEC SQL
DECLARE BLOBDESC CURSOR FOR
SELECT GUIDEBOOK
FROM TOURISM
WHERE STATE = ’CA’;

<RXGHILQH%OREFROXPQVWKHVDPHZD\\RXGHILQHQRQ%OREFROXPQV
7KHIROORZLQJ64/FRGHFUHDWHVDWDEOHZLWKD%OREFROXPQFDOOHG352-B'(6&,WVHWVWKH
VXEW\SHSDUDPHWHUWRZKLFKGHQRWHVD7(;7%OREDQGVHWVWKHVHJPHQWVL]HWRE\WHV
CREATE TABLE PROJECT
(
PROJ_ID PROJNO NOT NULL,
PROJ_NAME VARCHAR(20) NOT NULL UNIQUE,
PROJ_DESC BLOB SUBTYPE 1 SEGMENT SIZE 80,
TEAM_LEADER EMPNO,
PRODUCT PRODTYPE,
...
);

7KHIROORZLQJGLDJUDPVKRZVWKHUHODWLRQVKLSEHWZHHQD%OREFROXPQFRQWDLQLQJD%ORE,'
DQGWKH%OREGDWDUHIHUHQFHGE\WKH%ORE,'

170 INTERBASE 5
HOW ARE BLOB DATA STORED?

FIGURE 8.1 Relationship of a Blob ID to Blob segments in a database

Blob
column
Table row … Blob ID …

Blob data segment segment segment …

5DWKHUWKDQVWRUH%OREGDWDGLUHFWO\LQWKHWDEOH,QWHU%DVHVWRUHVD%ORE,'LQHDFKURZRI
WKHWDEOH7KH%ORE,'DXQLTXHQXPEHUSRLQWVWRWKHILUVWVHJPHQWRIWKH%OREGDWDWKDWLV
VWRUHGHOVHZKHUHLQWKHGDWDEDVHLQDVHULHVRIVHJPHQWV:KHQDQDSSOLFDWLRQFUHDWHVD%ORE
LWPXVWZULWHGDWDWRWKDW%OREDVHJPHQWDWDWLPH6LPLODUO\ZKHQDQDSSOLFDWLRQUHDGVRI
%ORELWUHDGVDVHJPHQWDWDWLPH%HFDXVHPRVW%OREGDWDDUHODUJHREMHFWVPRVW%ORE
PDQDJHPHQWLVSHUIRUPHGZLWKORRSVLQWKHDSSOLFDWLRQFRGH

Blob segment length


:KHQ\RXGHILQHD%ORELQDWDEOH\RXVSHFLI\WKHH[SHFWHGVL]HRI%OREVHJPHQWVWKDWDUH
WREHZULWWHQWRWKHFROXPQLQWKH%OREGHILQLWLRQVWDWHPHQW7KHVHJPHQWOHQJWK\RXGHILQH
IRUD%OREFROXPQVSHFLILHVWKHPD[LPXPQXPEHURIE\WHVWKDWDQDSSOLFDWLRQLVH[SHFWHGWR
ZULWHWRRUUHDGIURPDQ\%ORELQWKHFROXPQ7KHGHIDXOWVHJPHQWOHQJWKLV)RUH[DPSOH
WKHIROORZLQJFROXPQGHFODUDWLRQFUHDWHVD%OREZLWKDVHJPHQWOHQJWKRI
EXEC SQL CREATE TABLE TABLE2
(
Blob1 Blob SEGMENT SIZE 120;
);

,QWHU%DVHXVHVWKHVHJPHQWOHQJWKVHWWLQJWRGHWHUPLQHWKHVL]HRIDQLQWHUQDOEXIIHUWRZKLFK
LWZULWHV%OREVHJPHQWGDWD1RUPDOO\\RXVKRXOGQRWDWWHPSWWRZULWHVHJPHQWVODUJHUWKDQ
WKHVHJPHQWOHQJWK\RXGHILQHGLQWKHWDEOHGRLQJVRPD\UHVXOWLQDEXIIHURYHUIORZDQG
SRVVLEOHPHPRU\FRUUXSWLRQ
6SHFLI\LQJDVHJPHQWVL]HRIQJXDUDQWHHVWKDWQRPRUHWKDQQQXPEHURIE\WHVDUHUHDGRU
ZULWWHQLQDVLQJOH%ORERSHUDWLRQ:LWKVRPHW\SHVRIRSHUDWLRQVIRULQVWDQFHZLWK6(/(&7
,16(57DQG83'$7(RSHUDWLRQV\RXFDQUHDGRUZULWH%OREVHJPHQWVRIYDU\LQJOHQJWK
,QWKHIROORZLQJH[DPSOHRIDQ,16(57&85625VWDWHPHQWVSHFLI\WKHVHJPHQWOHQJWKLQD
KRVWODQJXDJHYDULDEOHVHJPHQWBOHQJWKDVIROORZV

PROGRAMMER’S GUIDE 171


CHAPTER 8 WORKING WITH BLOB DATA

EXEC SQL
INSERT CURSOR BCINS VALUES (:write_segment_buffer
INDICATOR :segment_length);

)RUPRUHLQIRUPDWLRQDERXWWKHV\QWD[RIWKH,16(57&85625VWDWHPHQWVHHWKH/DQJXDJH
5HIHUHQFH

Overriding segment length


<RXFDQRYHUULGHWKHVHJPHQWOHQJWKVHWWLQJE\LQFOXGLQJWKH0$;,080B6(*0(17RSWLRQ
LQD'(&/$5(&85625VWDWHPHQW)RUH[DPSOHWKHIROORZLQJ%ORE,16(57FXUVRU
GHFODUDWLRQRYHUULGHVWKHVHJPHQWOHQJWKWKDWZDVGHILQHGIRUWKHILHOG%ORELQFUHDVLQJLW
WR
EXEC SQL
DECLARE BCINS CURSOR FOR INSERT Blob Blob2 INTO TABLE 2
MAXIMUM_SEGMENT 1024;
Note %\RYHUULGLQJWKHVHJPHQWOHQJWKVHWWLQJ\RXDIIHFWRQO\WKHVHJPHQWVL]HIRUWKH
FXUVRUQRWIRUWKHFROXPQRUIRURWKHUFXUVRUV2WKHUFXUVRUVXVLQJWKHVDPH%OREFROXPQ
PDLQWDLQWKHRULJLQDOVHJPHQWVL]HWKDWZDVGHILQHGLQWKHFROXPQGHILQLWLRQRUFDQVSHFLI\
WKHLURZQRYHUULGHV
7KHVHJPHQWOHQJWKVHWWLQJGRHVQRWDIIHFW,QWHU%DVHV\VWHPSHUIRUPDQFH&KRRVHWKH
VHJPHQWOHQJWKPRVWFRQYHQLHQWIRUWKHVSHFLILFDSSOLFDWLRQ7KHODUJHVWSRVVLEOHVHJPHQW
OHQJWKLVE\WHV . 

Accessing Blob data with SQL


,QWHU%DVHVXSSRUWV6(/(&7,16(5783'$7(DQG'(/(7(RSHUDWLRQVRQ%OREGDWD7KH
IROORZLQJVHFWLRQVFRQWDLQEULHIGLVFXVVLRQVRIH[DPSOHSURJUDPV7KHVHSURJUDPVLOOXVWUDWH
KRZWRSHUIRUPVWDQGDUG64/RSHUDWLRQVRQ%OREGDWD

Selecting Blob data


7KHIROORZLQJH[DPSOHSURJUDPVHOHFWV%OREGDWDIURPWKH*8,'(%22.FROXPQRIWKH
7285,60WDEOH
 'HFODUHKRVWODQJXDJHYDULDEOHVWRVWRUHWKH%ORE,'WKH%OREVHJPHQWGDWDDQG
WKHOHQJWKRIVHJPHQWGDWD
EXEC SQL

172 INTERBASE 5
ACCESSING BLOB DATA WITH SQL

BEGIN DECLARE SECTION;


BASED ON TOURISM.GUIDEBOOK blob_id;
BASED ON TOURISM.GUIDEBOOK.SEGMENT blob_segment_buf;
BASED ON TOURISM.STATE state;
unsigned short blob_seg_len;
EXEC SQL
END DECLARE SECTION;

7KH%$6('21«6(*0(17V\QWD[GHFODUHVDKRVWODQJXDJHYDULDEOHEOREBVHJPHQWBEXI
WKDWLVODUJHHQRXJKWRKROGD%OREVHJPHQWGXULQJD)(7&+RSHUDWLRQ)RUPRUH
LQIRUPDWLRQDERXWWKH%$6('21VWDWHPHQWVHHWKH/DQJXDJH5HIHUHQFH
 'HFODUHDWDEOHFXUVRUWRVHOHFWWKHGHVLUHG%OREFROXPQLQWKLVFDVHWKH
*8,'(%22.FROXPQ
EXEC SQL
DECLARE TC CURSOR FOR
SELECT STATE, GUIDEBOOK
FROM TOURISM
WHERE STATE = ’CA’;

 'HFODUHD%OREUHDGFXUVRU$%OREUHDGFXUVRULVDVSHFLDOFXUVRUXVHGIRUUHDGLQJ
%OREVHJPHQWV
EXEC SQL
DECLARE BC CURSOR FOR
READ Blob GUIDEBOOK
FROM TOURISM;

7KHVHJPHQWOHQJWKRIWKH*8,'(%22.%OREFROXPQLVGHILQHGDVVR%OREFXUVRU
%&UHDGVDPD[LPXPRIE\WHVDWDWLPH
7RRYHUULGHWKHVHJPHQWOHQJWKVSHFLILHGLQWKHGDWDEDVHVFKHPDIRU*8,'(%22.XVH
WKH0$;,080B6(*0(17RSWLRQ)RUH[DPSOHWKHIROORZLQJFRGHUHVWULFWVHDFK%ORE
UHDGRSHUDWLRQWRDPD[LPXPRIE\WHVDQG64/&2'(LVVHWWRWRLQGLFDWHZKHQ
RQO\DSRUWLRQRIDVHJPHQWKDVEHHQUHDG
EXEC SQL
DECLARE BC CURSOR FOR
READ Blob GUIDEBOOK
FROM TOURISM
MAXIMUM_SEGMENT 40;

1RPDWWHUZKDWWKHVHJPHQWOHQJWKVHWWLQJLVRQO\RQHVHJPHQWLVUHDGDWDWLPH
 2SHQWKHWDEOHFXUVRUDQGIHWFKDURZRIGDWDFRQWDLQLQJD%ORE
EXEC SQL
OPEN TC;

PROGRAMMER’S GUIDE 173


CHAPTER 8 WORKING WITH BLOB DATA

EXEC SQL
FETCH TC INTO :state, :blob_id;

7KH)(7&+VWDWHPHQWIHWFKHVWKH67$7(DQG*8,'(%22.FROXPQVLQWRKRVWYDULDEOHV
VWDWHDQGEOREBLGUHVSHFWLYHO\
 2SHQWKH%OREUHDGFXUVRUXVLQJWKH%ORE,'VWRUHGLQWKHEOREBLGYDULDEOHDQG
IHWFKWKHILUVWVHJPHQWRI%OREGDWD
EXEC SQL
OPEN BC USING :blob_id;
EXEC SQL
FETCH BC INTO :blob_segment_buf:blob_seg_len;

:KHQWKH)(7&+RSHUDWLRQFRPSOHWHVEOREBVHJPHQWBEXIFRQWDLQVWKHILUVWVHJPHQWRIWKH
%OREDQGEOREBVHJBOHQFRQWDLQVWKHVHJPHQW·VOHQJWKZKLFKLVWKHQXPEHURIE\WHVFRSLHG
LQWREOREBVHJPHQWBEXI
 )HWFKWKHUHPDLQLQJVHJPHQWVLQDORRS64/&2'(VKRXOGEHFKHFNHGHDFKWLPH
DIHWFKLVSHUIRUPHG$QHUURUFRGHRILQGLFDWHVWKDWDOORIWKH%OREGDWDKDV
EHHQIHWFKHG$QHUURUFRGHRILQGLFDWHVWKDWWKHVHJPHQWFRQWDLQV
DGGLWLRQDOGDWD
while (SQLCODE != 100 || SQLCODE == 101)
{
printf("%*.*s", blob_seg_len, blob_seg_len, blob_segment_buf);
EXEC SQL
FETCH BC INTO :blob_segment_buf:blob_seg_len;
}

,QWHU%DVHSURGXFHVDQHUURUFRGHRIZKHQWKHOHQJWKRIWKHVHJPHQWEXIIHULVOHVV
WKDQWKHOHQJWKRIDSDUWLFXODUVHJPHQW
)RUH[DPSOHLIWKHOHQJWKRIWKHVHJPHQWEXIIHULVDQGWKHOHQJWKRIDSDUWLFXODU
VHJPHQWLVWKHILUVW)(7&+SURGXFHVDQHUURUFRGHRILQGLFDWLQJWKDWGDWDUHPDLQV
LQWKHVHJPHQW7KHVHFRQG)(7&+UHDGVWKHUHPDLQLQJE\WHVRIGDWDDQGSURGXFHV
DQ64/&2'(RILQGLFDWLQJWKDWWKHQH[WVHJPHQWLVUHDG\WREHUHDGRULIWKLVZDV
WKHODVWVHJPHQWLQWKH%ORE
 &ORVHWKH%OREUHDGFXUVRU
EXEC SQL
CLOSE BC;

 &ORVHWKHWDEOHFXUVRU
EXEC SQL
CLOSE TC;

174 INTERBASE 5
ACCESSING BLOB DATA WITH SQL

Inserting Blob data


7KHIROORZLQJSURJUDPLQVHUWV%OREGDWDLQWRWKH*8,'(%22.FROXPQRIWKH7285,60
WDEOH
 'HFODUHKRVWODQJXDJHYDULDEOHVWRVWRUHWKH%ORE,'%OREVHJPHQWGDWDDQGWKH
OHQJWKRIVHJPHQWGDWD
EXEC SQL
BEGIN DECLARE SECTION;
BASED ON TOURISM.GUIDEBOOK blob_id;
BASED ON TOURISM.GUIDEBOOK.SEGMENT blob_segment_buf;
BASED ON TOURISM.STATE state;
unsigned short blob_seg_len;
EXEC SQL
END DECLARE SECTION;

à 7KH%$6('21«6(*0(17V\QWD[GHFODUHVDKRVWODQJXDJHYDULDEOHEOREBVHJPHQWBEXIWKDW
LVODUJHHQRXJKWRKROGD%OREVHJPHQWGXULQJD)(7&+RSHUDWLRQ)RUPRUHLQIRUPDWLRQ
DERXWWKH%$6('21GLUHFWLYHVHHWKH/DQJXDJH5HIHUHQFH
 'HFODUHD%ORELQVHUWFXUVRU
EXEC SQL
DECLARE BC CURSOR FOR INSERT Blob GUIDEBOOK INTO TOURISM;

 2SHQWKH%ORELQVHUWFXUVRUDQGVSHFLI\WKHKRVWYDULDEOHLQZKLFKWRVWRUHWKH
%ORE,'
EXEC SQL
OPEN BC INTO :blob_id;

 6WRUHWKHVHJPHQWGDWDLQWKHVHJPHQWEXIIHUEOREBVHJPHQWBEXIFDOFXODWHWKH
OHQJWKRIWKHVHJPHQWGDWDDQGXVHDQ,16(57&85625VWDWHPHQWWRZULWHWKH
VHJPHQW
sprintf(blob_segment_buf, ’We hold these truths to be self evident’);
blob_segment_len = strlen(blob_segment_buf);

EXEC SQL
INSERT CURSOR BC VALUES (:blob_segment_buf:blob_segment_len);

5HSHDWWKHVHVWHSVLQDORRSXQWLO\RXKDYHZULWWHQDOO%OREVHJPHQWV
 &ORVHWKH%ORELQVHUWFXUVRU
EXEC SQL
CLOSE BC;

PROGRAMMER’S GUIDE 175


CHAPTER 8 WORKING WITH BLOB DATA

 8VHDQ,16(57VWDWHPHQWWRLQVHUWDQHZURZFRQWDLQLQJWKH%ORELQWRWKH
7285,60WDEOH
EXEC SQL
INSERT INTO TOURISM (STATE,GUIDEBOOK) VALUES (’CA’,:blob_id);

 &RPPLWWKHFKDQJHVWRWKHGDWDEDVH
EXEC SQL
COMMIT;

Updating Blob data


<RXFDQQRWXSGDWHD%OREGLUHFWO\<RXPXVWFUHDWHDQHZ%OREUHDGWKHROG%OREGDWDLQWR
DEXIIHUZKHUH\RXFDQHGLWRUPRGLI\LWWKHQZULWHWKHPRGLILHGGDWDWRWKHQHZ%ORE
&UHDWHDQHZ%OREE\IROORZLQJWKHVHVWHSV
 'HFODUHD%ORELQVHUWFXUVRU
EXEC SQL
DECLARE BC CURSOR FOR INSERT BLOB GUIDEBOOK INTO TOURISM;

 2SHQWKH%ORELQVHUWFXUVRUDQGVSHFLI\WKHKRVWYDULDEOHLQZKLFKWRVWRUHWKH
%ORE,'
EXEC SQL
OPEN BC INTO :blob_id;

 6WRUHWKHROG%OREVHJPHQWGDWDLQWKHVHJPHQWEXIIHUEOREBVHJPHQWBEXIFDOFXODWH
WKHOHQJWKRIWKHVHJPHQWGDWDSHUIRUPDQ\PRGLILFDWLRQVWRWKHGDWDDQGXVH
DQ,16(57&85625VWDWHPHQWWRZULWHWKHVHJPHQW
/* Programmatically read the first/next segment of the old Blob
* segment data into blob_segment_buf; */
EXEC SQL
INSERT CURSOR BC VALUES (:blob_segment_buf:blob_segment_len);

5HSHDWWKHVHVWHSVLQDORRSXQWLO\RXKDYHZULWWHQDOO%OREVHJPHQWV
 &ORVHWKH%ORELQVHUWFXUVRU
EXEC SQL
CLOSE BC;

 :KHQ\RXKDYHFRPSOHWHGFUHDWLQJWKHQHZ%ORELVVXHDQ83'$7(VWDWHPHQWWR
UHSODFHWKHROG%ORELQWKHWDEOHZLWKWKHQHZRQHDVLQWKHIROORZLQJH[DPSOH
EXEC SQL UPDATE TOURISM
SET

176 INTERBASE 5
ACCESSING BLOB DATA WITH SQL

GUIDEBOOK = :blob_id;
WHERE CURRENT OF TC;
Note 7KH7&WDEOHFXUVRUSRLQWVWRDWDUJHWURZHVWDEOLVKHGE\GHFODULQJWKHFXUVRUDQGWKHQ
IHWFKLQJWKHURZWRXSGDWH
7RPRGLI\DWH[W%OREXVLQJWKLVWHFKQLTXH\RXPLJKWUHDGDQH[LVWLQJ%OREILHOGLQWRD
KRVWODQJXDJHEXIIHUPRGLI\WKHGDWDWKHQZULWHWKHPRGLILHGEXIIHURYHUWKHH[LVWLQJILHOG
GDWDZLWKDQ83'$7(VWDWHPHQW

Deleting Blob data


7KHUHDUHWZRPHWKRGVIRUGHOHWLQJD%ORE7KHILUVWLVWRGHOHWHWKHURZFRQWDLQLQJWKH%ORE
7KHVHFRQGLVWRXSGDWHWKHURZDQGVHWWKH%OREFROXPQWR18//RUWRWKH%ORE,'RID
GLIIHUHQW%ORE IRUH[DPSOHWKHQHZ%OREFUHDWHGWRXSGDWHWKHGDWDRIDQH[LVWLQJ%ORE 
7KHIROORZLQJVWDWHPHQWGHOHWHVFXUUHQW%OREGDWDLQWKH*8,'(%22.FROXPQRIWKH
7285,60WDEOHE\VHWWLQJLWWR18//
EXEC SQL UPDATE TOURISM
SET
GUIDEBOOK = NULL;
WHERE CURRENT OF TC;

%OREGDWDLVQRWLPPHGLDWHO\GHOHWHGZKHQ'(/(7(LVVSHFLILHG7KHDFWXDOGHOHWHRSHUDWLRQ
RFFXUVZKHQ,QWHU%DVHSHUIRUPVYHUVLRQFOHDQXS7KHIROORZLQJFRGHIUDJPHQWLOOXVWUDWHV
KRZWRUHFRYHUVSDFHDIWHUGHOHWLQJD%ORE
EXEC SQL
UPDATE TABLE SET Blob_COLUMN = NULL WHERE ROW = :myrow;
EXEC SQL
COMMIT;
/* wait for all active transactions to finish */
/* force a sweep of the database */

:KHQ,QWHU%DVHSHUIRUPVJDUEDJHFROOHFWLRQRQROGYHUVLRQVRIDUHFRUGLWYHULILHVZKHWKHU
RUQRWUHFHQWYHUVLRQVRIWKHUHFRUGUHIHUHQFHWKH%ORE,',IWKHUHFRUGGRHVQRWUHIHUHQFH
WKH%ORE,',QWHU%DVHFOHDQVXSWKH%ORE

PROGRAMMER’S GUIDE 177


CHAPTER 8 WORKING WITH BLOB DATA

Accessing Blob data with API calls


,QDGGLWLRQWRDFFHVVLQJ%OREGDWDXVLQJ64/DVGHVFULEHGLQWKLVFKDSWHUWKH,QWHU%DVH$3,
SURYLGHVURXWLQHVIRUDFFHVVLQJ%OREGDWD7KHIROORZLQJ$3,FDOOVDUHSURYLGHGIRUDFFHVVLQJ
DQGPDQDJLQJ%OREGDWD

Function Description
isc_blob_default_desc() Loads a Blob descriptor data structure with default information about
a Blob.
isc_blob_gen_bpb() Generates a Blob parameter buffer (BPB) from source and target Blob
descriptors to allow dynamic access to Blob subtype and character set
information.
isc_blob_info() Returns information about an open Blob.
isc_blob_lookup_desc() Looks up and stores into a Blob descriptor the subtype, character set,
and segment size of a Blob.
isc_blob_set_desc() Sets the fields of a Blob descriptor to values specified in parameters to
isc_blob_set_desc().
isc_cancel_blob() Discards a Blob and frees internal storage.
isc_close_blob() Closes an open Blob.
isc_create_blob2() Creates a context for storing a Blob, opens the Blob for write access,
and optionally specifies a filter to be used to translate the Blob data
from one subtype to another.
isc_get_segment() Reads a segment from an open Blob.
isc_open_blob2() Opens an existing Blob for retrieval and optional filtering.
isc_put_segment() Writes a Blob segment.
TABLE 8.2 API Blob calls

)RUGHWDLOVRQXVLQJWKH$3,FDOOVWRDFFHVV%OREGDWDVHHWKH$3,*XLGH

178 INTERBASE 5
FILTERING BLOB DATA

Filtering Blob data


$QXQGHUVWDQGLQJRI%OREVXEW\SHVLVSDUWLFXODUO\LPSRUWDQWZKHQZRUNLQJZLWK%OREILOWHUV
$%OREILOWHULVDURXWLQHWKDWWUDQVODWHV%OREGDWDIURPRQHVXEW\SHWRDQRWKHU,QWHU%DVH
LQFOXGHVDVHWRIVSHFLDOLQWHUQDO%OREILOWHUVWKDWFRQYHUWIURPVXEW\SHWRVXEW\SH 7(;7 
DQGIURPVXEW\SH 7(;7 WRVXEW\SH,QDGGLWLRQWRXVLQJWKHVHVWDQGDUGILOWHUV\RXFDQ
ZULWH\RXURZQH[WHUQDOILOWHUVWRSURYLGHVSHFLDOGDWDWUDQVODWLRQ)RUH[DPSOH\RXPLJKW
GHYHORSDILOWHUWRWUDQVODWHELWPDSSHGLPDJHVIURPRQHIRUPDWWRDQRWKHU

,03257$17 %OREILOWHUVDUHDYDLODEOHIRUGDWDEDVHVUHVLGLQJRQDOO,QWHU%DVHVHUYHUSODWIRUPVH[FHSW
1HW:DUHZKHUH%OREILOWHUVFDQQRWEHFUHDWHGRUXVHG

Using the standard InterBase text filters


7KHVWDQGDUG,QWHU%DVHILOWHUVFRQYHUW%OREGDWDRIVXEW\SHRUDQ\,QWHU%DVHV\VWHPW\SH
WRVXEW\SH 7(;7 
:KHQDWH[WILOWHULVEHLQJXVHGWRUHDGGDWDIURPD%OREFROXPQLWPRGLILHVWKHVWDQGDUG
,QWHU%DVHEHKDYLRUIRUVXSSO\LQJVHJPHQWV5HJDUGOHVVRIWKHDFWXDOQDWXUHRIWKHVHJPHQWV
LQWKH%OREFROXPQWKHWH[WILOWHUHQIRUFHVWKHUXOHWKDWVHJPHQWVPXVWHQGZLWKDQHZOLQH
FKDUDFWHU ?Q 
7KHWH[WILOWHUUHWXUQVDOOWKHFKDUDFWHUVXSWRDQGLQFOXGLQJWKHILUVWQHZOLQHDVWKHILUVW
VHJPHQWWKHQH[WFKDUDFWHUVXSWRDQGLQFOXGLQJWKHVHFRQGQHZOLQHDVWKHVHFRQGVHJPHQW
DQGVRRQ

7,3 7RFRQYHUWDQ\QRQWH[WVXEW\SHWR7(;7GHFODUHLWV)520VXEW\SHDVVXEW\SHDQGLWV72
VXEW\SHDVVXEW\SH

Using an external Blob filter


8QOLNHWKHVWDQGDUG,QWHU%DVHILOWHUVWKDWFRQYHUWEHWZHHQVXEW\SHDQGVXEW\SHDQ
H[WHUQDO%OREILOWHULVJHQHUDOO\SDUWRIDOLEUDU\RIURXWLQHV\RXFUHDWHDQGOLQNWR\RXU
DSSOLFDWLRQ
7RXVHDQH[WHUQDOILOWHU\RXPXVWILUVWZULWHLWFRPSLOHDQGOLQNLWWKHQGHFODUHLWWRWKH
GDWDEDVHWKDWFRQWDLQVWKH%OREGDWD\RXZDQWSURFHVVHG

PROGRAMMER’S GUIDE 179


CHAPTER 8 WORKING WITH BLOB DATA

4 'HFODULQJDQH[WHUQDOILOWHUWRWKHGDWDEDVH
7RGHFODUHDQH[WHUQDOILOWHUWRDGDWDEDVHXVHWKH'(&/$5(),/7(5VWDWHPHQW)RUH[DPSOH
WKHIROORZLQJVWDWHPHQWGHFODUHVWKHILOWHU6$03/(
EXEC SQL
DECLARE FILTER SAMPLE
INPUT_TYPE -1 OUTPUT_TYPE -2
ENTRY_POINT "FilterFunction"
MODULE_NAME "filter.dll";

,QWKHH[DPSOHWKHILOWHU·VLQSXWVXEW\SHLVGHILQHGDVDQGLWVRXWSXWVXEW\SHDV,QWKLV
H[DPSOH,1387B7<3(VSHFLILHVORZHUFDVHWH[WDQG287387B7<3(VSHFLILHVXSSHUFDVHWH[W
7KHSXUSRVHRIILOWHU6$03/(WKHUHIRUHLVWRWUDQVODWH%OREGDWDIURPORZHUFDVHWH[WWR
XSSHUFDVHWH[W
7KH(175<B32,17DQG02'8/(B1$0(SDUDPHWHUVVSHFLI\WKHH[WHUQDOURXWLQHWKDW
,QWHU%DVHFDOOVZKHQWKHILOWHULVLQYRNHG7KH02'8/(B1$0(SDUDPHWHUVSHFLILHVILOWHUGOO
WKHG\QDPLFOLQNOLEUDU\FRQWDLQLQJWKHILOWHU·VH[HFXWDEOHFRGH7KH(175<B32,17
SDUDPHWHUVSHFLILHVWKHHQWU\SRLQWLQWRWKH'//7KHH[DPSOHVKRZVRQO\DVLPSOHILOHQDPH
,WLVJRRGSUDFWLFHWRVSHFLI\DIXOO\TXDOLILHGSDWKQDPHVLQFHXVHUVRI\RXUDSSOLFDWLRQQHHG
WRORDGWKHILOH

4 8VLQJDILOWHUWRUHDGDQGZULWH%OREGDWD
7KHIROORZLQJLOOXVWUDWLRQVKRZVWKHGHIDXOWEHKDYLRURIWKH6$03/(ILOWHUWKDWWUDQVODWHV
IURPORZHUFDVHWH[WWRXSSHUFDVHWH[W

FIGURE 8.2 Filtering from lowercase to uppercase

Application Blob
Filter:
abcdef SAMPLE ABCDEF

6LPLODUO\ZKHQUHDGLQJGDWDWKH6$03/(ILOWHUFDQHDVLO\UHDG%OREGDWDRIVXEW\SHDQG
WUDQVODWHLWWRGDWDRIVXEW\SH

180 INTERBASE 5
WRITING AN EXTERNAL BLOB FILTER

FIGURE 8.3 Filtering from uppercase to lowercase

Blob Application
Filter:
ABCDEF SAMPLE abcdef

4 ,QYRNLQJDILOWHULQDQDSSOLFDWLRQ
7RLQYRNHDILOWHULQDQDSSOLFDWLRQXVHWKH),/7(5RSWLRQZKHQGHFODULQJD%OREFXUVRU
7KHQZKHQWKHDSSOLFDWLRQSHUIRUPVRSHUDWLRQVXVLQJWKHFXUVRU,QWHU%DVHDXWRPDWLFDOO\
LQYRNHVWKHILOWHU
)RUH[DPSOHWKHIROORZLQJ,16(57FXUVRUGHILQLWLRQVSHFLILHVWKDWWKHILOWHU6$03/(LVWR
EHXVHGLQDQ\RSHUDWLRQVLQYROYLQJWKHFXUVRU%&,16
EXEC SQL
DECLARE BCINS1 CURSOR FOR
INSERT Blob Blob1 INTO TABLE1
FILTER FROM -1 TO -2;

:KHQ,QWHU%DVHSURFHVVHVWKLVGHFODUDWLRQLWVHDUFKHVDOLVWRIILOWHUVGHILQHGLQWKHFXUUHQW
GDWDEDVHIRUDILOWHUZLWKPDWFKLQJ)520DQG72VXEW\SHV,IVXFKDILOWHUH[LVWV,QWHU%DVH
LQYRNHVLWGXULQJ%ORERSHUDWLRQVWKDWXVHWKHFXUVRU%&,16,I,QWHU%DVHFDQQRWORFDWHD
ILOWHUZLWKPDWFKLQJ)520DQG72VXEW\SHVLWUHWXUQVDQHUURUWRWKHDSSOLFDWLRQ

Writing an external Blob filter


,I\RXFKRRVHWRZULWH\RXURZQILOWHUV\RXPXVWKDYHDGHWDLOHGXQGHUVWDQGLQJRIWKH
GDWDW\SHV\RXSODQWRWUDQVODWH$VPHQWLRQHGHOVHZKHUHLQWKLVFKDSWHU,QWHU%DVHGRHVQRW
GRVWULFWGDWDW\SHFKHFNLQJRQ%OREGDWDEXWGRHVHQIRUFHWKHUXOHWKDW%OREVRXUFHDQG
WDUJHWVXEW\SHVPXVWEHFRPSDWLEOH0DLQWDLQLQJDQGHQIRUFLQJWKLVFRPSDWLELOLW\LV\RXU
UHVSRQVLELOLW\

PROGRAMMER’S GUIDE 181


CHAPTER 8 WORKING WITH BLOB DATA

Filter types
)LOWHUVFDQEHGLYLGHGLQWRWZRW\SHVILOWHUVWKDWFRQYHUWGDWDRQHVHJPHQWDWDWLPHDQGILOWHUV
WKDWFRQYHUWGDWDPDQ\VHJPHQWVDWDWLPH
7KHILUVWW\SHRIILOWHUUHDGVDVHJPHQWRIGDWDFRQYHUWVLWDQGVXSSOLHVLWWRWKHDSSOLFDWLRQ
DVHJPHQWDWDWLPH
7KHVHFRQGW\SHRIILOWHUPLJKWUHDGDOOWKHGDWDDQGGRDOOWKHFRQYHUVLRQZKHQWKH%OREUHDG
FXUVRULVILUVWRSHQHGDQGWKHQVLPXODWHVXSSO\LQJGDWDDVHJPHQWDWDWLPHWRWKHDSSOLFDWLRQ
,IWLPLQJLVDQLVVXHIRU\RXUDSSOLFDWLRQ\RXVKRXOGFDUHIXOO\FRQVLGHUWKHVHWZRW\SHVRI
ILOWHUVDQGZKLFKPLJKWEHWWHUVHUYH\RXUSXUSRVH

Read-only and write-only filters


6RPHILOWHUVPD\RQO\VXSSRUWUHDGLQJIURPRUZULWLQJWRD%OREEXWQRWERWKRSHUDWLRQV,I
\RXDWWHPSWWRXVHD%OREILOWHUIRUDQRSHUDWLRQWKDWLWGRHVQRWVXSSRUW,QWHU%DVHUHWXUQV
DQHUURUWRWKHDSSOLFDWLRQ

Defining the filter function


:KHQZULWLQJ\RXUILOWHU\RXPXVWLQFOXGHDQHQWU\SRLQWNQRZQDVDILOWHUIXQFWLRQLQWKH
GHFODUDWLRQVHFWLRQRIWKHSURJUDP,QWHU%DVHFDOOVWKHILOWHUIXQFWLRQZKHQ\RXUDSSOLFDWLRQ
SHUIRUPVD%OREDFFHVVRSHUDWLRQ$OOFRPPXQLFDWLRQEHWZHHQ,QWHU%DVHDQGWKHILOWHULV
WKURXJKWKHILOWHUIXQFWLRQ7KHILOWHUIXQFWLRQLWVHOIPD\FDOORWKHUIXQFWLRQVWKDWFRPSULVH
WKHILOWHUH[HFXWDEOH

FIGURE 8.4 Filter interaction with an application and a database

APPLICATION

INTERBASE

FILTER

182 INTERBASE 5
WRITING AN EXTERNAL BLOB FILTER

'HFODUHWKHQDPHRIWKHILOWHUIXQFWLRQDQGWKHQDPHRIWKHILOWHUH[HFXWDEOHZLWKWKH
(175<B32,17DQG02'8/(B1$0(SDUDPHWHUVRIWKH'(&/$5(),/7(5VWDWHPHQW
$ILOWHUIXQFWLRQPXVWKDYHWKHIROORZLQJGHFODUDWLRQFDOOLQJVHTXHQFH
filter_function_name(short action, isc_blob_ctl control);

7KHSDUDPHWHUDFWLRQLVRQHRIHLJKWSRVVLEOHDFWLRQPDFURGHILQLWLRQVDQGWKHSDUDPHWHU
FRQWUROLVDQLQVWDQFHRIWKHLVFBEOREBFWO%OREFRQWUROVWUXFWXUHGHILQHGLQWKH,QWHU%DVHKHDGHU
ILOHLEDVHK7KHVHSDUDPHWHUVDUHGLVFXVVHGODWHULQWKLVFKDSWHU
7KHIROORZLQJOLVWLQJRIDVNHOHWRQILOWHUGHFODUHVWKHILOWHUIXQFWLRQMSHJBILOWHU
#include <ibase.h>

#define SUCCESS 0
#define FAILURE 1

ISC_STATUS jpeg_filter(short action, isc_blob_ctl control)


{
ISC_STATUS status = SUCCESS;

switch (action)
{
case isc_blob_filter_open:
. . .
break;
case isc_blob_filter_get_segment:
. . .
break;
case isc_blob_filter_create:
. . .
break;
case isc_blob_filter_put_segment:
. . .
break;
case isc_blob_filter_close:
. . .
break;
case isc_blob_filter_alloc:
. . .
break;
case isc_blob_filter_free:
. . .
break;
case isc_blob_filter_seek:

PROGRAMMER’S GUIDE 183


CHAPTER 8 WORKING WITH BLOB DATA

. . .
break;
default:
status = isc_uns_ext /* unsupported action value */
. . .
break;
}
return status;
}

,QWHU%DVHSDVVHVRQHRIHLJKWSRVVLEOHDFWLRQVWRWKHILOWHUIXQFWLRQjpeg_filter()E\ZD\RI
WKHDFWLRQSDUDPHWHUDQGDOVRSDVVHVDQLQVWDQFHRIWKH%OREFRQWUROVWUXFWXUHLVFBEOREBFWOE\
ZD\RIWKHSDUDPHWHUFRQWURO
7KHHOOLSVHV « LQWKHSUHYLRXVOLVWLQJUHSUHVHQWFRGHWKDWSHUIRUPVVRPHRSHUDWLRQVEDVHG
RQHDFKDFWLRQRUHYHQWWKDWLVOLVWHGLQWKHFDVHVWDWHPHQW(DFKDFWLRQLVDSDUWLFXODUHYHQW
LQYRNHGE\DGDWDEDVHRSHUDWLRQWKHDSSOLFDWLRQPLJKWSHUIRUP)RUPRUHLQIRUPDWLRQVHH
´3URJUDPPLQJILOWHUIXQFWLRQDFWLRQVµRQSDJH 
7KHLVFBEOREBFWO%OREFRQWUROVWUXFWXUHSURYLGHVWKHIXQGDPHQWDOGDWDH[FKDQJHEHWZHHQ
,QWHU%DVHDQGWKHILOWHU)RUPRUHLQIRUPDWLRQRQWKH%OREFRQWUROVWUXFWXUHVHH´'HILQLQJ
WKH%OREFRQWUROVWUXFWXUHµRQSDJH 

4 'HILQLQJWKH%OREFRQWUROVWUXFWXUH
7KH%OREFRQWUROVWUXFWXUHLVFBEOREBFWOSURYLGHVWKHIXQGDPHQWDOPHWKRGRIGDWDH[FKDQJH
EHWZHHQ,QWHU%DVHDQGDILOWHU7KHGHFODUDWLRQIRUWKHLVFBEOREBFWOFRQWUROVWUXFWXUHLVLQWKH
,QWHU%DVHLQFOXGHILOHLEDVHK
7KHLVFBEOREBFWOVWUXFWXUHLVXVHGLQWZRZD\V
 :KHQWKHDSSOLFDWLRQSHUIRUPVD%OREDFFHVVRSHUDWLRQ,QWHU%DVHFDOOVWKHILOWHU
IXQFWLRQDQGSDVVHVLWDQLQVWDQFHRILVFBEOREBFWO
 ,QWHUQDOILOWHUIXQFWLRQVFDQSDVVDQLQVWDQFHRILVFBEOREBFWOWRLQWHUQDO,QWHU%DVH
DFFHVVURXWLQHV
,QHLWKHUFDVHWKHSXUSRVHRIFHUWDLQLVFBEOREBFWOILHOGVGHSHQGVRQWKHDFWLRQEHLQJ
SHUIRUPHG
)RUH[DPSOHZKHQDQDSSOLFDWLRQDWWHPSWVD%ORE,16(57,QWHU%DVHSDVVHVDQ
LVFBEOREBILOWHUBSXWBVHJPHQWDFWLRQWRWKHILOWHUIXQFWLRQ7KHILOWHUIXQFWLRQSDVVHVDQLQVWDQFHRI
WKHFRQWUROVWUXFWXUHWR,QWHU%DVH7KHFWOBEXIIHURIWKHVWUXFWXUHFRQWDLQVWKHVHJPHQWGDWD
WREHZULWWHQDVVSHFLILHGE\WKHDSSOLFDWLRQLQLWV%ORE,16(57VWDWHPHQW%HFDXVHWKHEXIIHU
FRQWDLQVLQIRUPDWLRQWRSDVVLQWRWKHILOWHUIXQFWLRQLWLVFDOOHGDQ,1ILHOG7KHILOWHUIXQFWLRQ
VKRXOGLQFOXGHLQVWUXFWLRQVLQWKHFDVHVWDWHPHQWXQGHUWKHLVFBEOREBILOWHUBSXWBVHJPHQWFDVHIRU
SHUIRUPLQJWKHZULWHWRWKHGDWDEDVH

184 INTERBASE 5
WRITING AN EXTERNAL BLOB FILTER

,QDGLIIHUHQWFDVHIRULQVWDQFHZKHQDQDSSOLFDWLRQDWWHPSWVD)(7&+RSHUDWLRQWKHFDVHRI
DQLVFBEOREBILOWHUBJHWBVHJPHQWDFWLRQVKRXOGLQFOXGHLQVWUXFWLRQVIRUILOOLQJFWOBEXIIHUZLWK
VHJPHQWGDWDIURPWKHGDWDEDVHWRUHWXUQWRWKHDSSOLFDWLRQ,QWKLVFDVHEHFDXVHWKHEXIIHU
LVXVHGIRUILOWHUIXQFWLRQRXWSXWLWLVFDOOHGDQRXWILHOG
7KHIROORZLQJWDEOHGHVFULEHVHDFKRIWKHILHOGVLQWKHLVFBEOREBFWO%OREFRQWUROVWUXFWXUHDQG
ZKHWKHUWKH\DUHXVHGIRUILOWHUIXQFWLRQLQSXW ,1 RURXWSXW 287 

Field name Description


(*ctl_source)() Pointer to the internal InterBase Blob access routine. (IN)
*ctl_source_handle Pointer to an instance of isc_blob_ctl to be passed to the internal InterBase Blob
access routine. (IN)
ctl_to_sub_type Target subtype. Information field. Provided to support multi-purpose filters that
can perform more than one kind of translation. This field and the next one enable
such a filter to decide which translation to perform. (IN)
ctl_from_sub_type Source subtype. Information field. Provided to support multi-purpose filters that
can perform more than one kind of translation. This field and the previous one
enable such a filter to decide which translation to perform. (IN)
ctl_buffer_length For isc_blob_filter_put_segment, field is an IN field that contains the length of the
segment data contained in ctl_buffer.
For isc_blob_filter_get_segment, field is an IN field set to the size of the buffer
pointed to by ctl_buffer, which is used to store the retrieved Blob data.
ctl_segment_length Length of the current segment. This field is not used for
isc_blob_filter_put_segment.
For isc_blob_filter_get_segment, the field is an OUT field set to the size of the
retrieved segment (or partial segment, in the case when the buffer length
ctl_buffer_length is less than the actual segment length).
ctl_bpb_length Length of the Blob parameter buffer. Reserved for future enhancement.
*ctl_bpb Pointer to a Blob parameter buffer. Reserved for future enhancement.
*ctl_buffer Pointer to a segment buffer. For isc_blob_filter_put_segment, field is an IN field
that contains the segment data.
For isc_blob_filter_get_segment, the field is an OUT field the filter function fills
with segment data for return to the application.
TABLE 8.3 isc_blob_ctl structure field descriptions

PROGRAMMER’S GUIDE 185


CHAPTER 8 WORKING WITH BLOB DATA

Field name Description


ctl_max_segment Length of longest segment in the Blob. Initial value is 0. The filter function sets this
field. This field is informational only.
ctl_number_segment Total number of segments in the Blob. Initial value is 0. The filter function sets this
s field. This field is informational only.
ctl_total_length Total length of the Blob. Initial value is 0. The filter function sets this field. This field
is informational only.
*ctl_status Pointer to the InterBase status vector. (OUT )
ctl_data[8] 8-element array of application-specific data. Use this field to store resource
pointers, such as memory pointers and file handles created by the
isc_blob_filter_open handler, for example. Then, the next time the filter function
is called, the resource pointers will be available for use. (IN/OUT )
TABLE 8.3 isc_blob_ctl structure field descriptions (continued)

SETTING CONTROL STRUCTURE INFORMATION FIELD VALUES


7KHLVFBEOREBFWOVWUXFWXUHFRQWDLQVWKUHHILHOGVWKDWVWRUHLQIRUPDWLRQDERXWWKH%OREFXUUHQWO\
EHLQJDFFHVVHGFWOBPD[BVHJPHQWFWOBQXPEHUBVHJPHQWVDQGFWOBWRWDOBOHQJWK
<RXVKRXOGDWWHPSWWRPDLQWDLQFRUUHFWYDOXHVIRUWKHVHILHOGVLQWKHILOWHUIXQFWLRQZKHQHYHU
SRVVLEOH'HSHQGLQJRQWKHSXUSRVHRIWKHILOWHUPDLQWDLQLQJFRUUHFWYDOXHVIRUWKHILHOGVLV
QRWDOZD\VSRVVLEOH)RUH[DPSOHDILOWHUWKDWFRPSUHVVHVGDWDRQDVHJPHQWE\VHJPHQWEDVLV
FDQQRWGHWHUPLQHWKHVL]HRIFWOBPD[BVHJPHQWXQWLOLWSURFHVVHVDOOVHJPHQWV
7KHVHILHOGVDUHLQIRUPDWLRQDORQO\,QWHU%DVHGRHVQRWXVHWKHYDOXHVRIWKHVHILHOGVLQ
LQWHUQDOSURFHVVLQJ

4 3URJUDPPLQJILOWHUIXQFWLRQDFWLRQV
:KHQDQDSSOLFDWLRQSHUIRUPVD%OREDFFHVVRSHUDWLRQ,QWHU%DVHSDVVHVDFRUUHVSRQGLQJ
DFWLRQPHVVDJHWRWKHILOWHUIXQFWLRQE\ZD\RIWKHDFWLRQSDUDPHWHU7KHUHDUHHLJKWSRVVLEOH
DFWLRQVHDFKRIZKLFKUHVXOWVIURPDSDUWLFXODUDFFHVVRSHUDWLRQ7KHIROORZLQJOLVWRIDFWLRQ
PDFURGHILQLWLRQVDUHGHFODUHGLQWKHLEDVHKILOH
#define isc_blob_filter_open 0
#define isc_blob_filter_get_segment 1
#define isc_blob_filter_close 2
#define isc_blob_filter_create 3
#define isc_blob_filter_put_segment 4
#define isc_blob_filter_alloc 5
#define isc_blob_filter_free 6
#define isc_blob_filter_seek 7

186 INTERBASE 5
WRITING AN EXTERNAL BLOB FILTER

7KHIROORZLQJWDEOHGHVFULEHVWKH%OREDFFHVVRSHUDWLRQWKDWFRUUHVSRQGVWRHDFKDFWLRQ

Action Invoked when … Use to …


isc_blob_filter_open Application opens a Blob READ Set the information fields of the Blob control structure.
cursor.
Perform initialization tasks, such as allocating memory
or opening temporary files.
Set the status variable, if necessary. The value of the
status variable becomes the filter function’s return
value.
isc_blob_filter_get_segment Application executes a Blob Set the ctl_buffer and ctl_segment_length fields of the
FETCH statement. Blob control structure to contain a segment’s worth of
translated data on the return of the filter function.
Perform the data translation if the filter processes the
Blob segment-by-segment.
Set the status variable. The value of the status variable
becomes the filter function’s return value.
isc_blob_filter_close Application closes a Blob cursor. Perform exit tasks, such as freeing allocated memory,
closing, or removing temporary files.
isc_blob_filter_create Application opens a Blob INSERT Set the information fields of the Blob control structure.
cursor.
Perform initialization tasks, such as allocating memory
or opening temporary files.
Set the status variable, if necessary. The value of the
status variable becomes the filter function’s return
value.
isc_blob_filter_put_segment Application executes a Blob Perform the data translation on the segment data
INSERT statement. passed in through the Blob control structure.
Write the segment data to the database. If the
translation process changes the segment length, the
new value must be reflected in the values passed to
the writing function.
Set the status variable. The value of the status variable
becomes the filter function’s return value.
TABLE 8.4 Blob access operations

PROGRAMMER’S GUIDE 187


CHAPTER 8 WORKING WITH BLOB DATA

Action Invoked when … Use to …


isc_blob_filter_alloc InterBase initializes filter Set the information fields of the Blob control structure.
processing. Not a result of a Perform initialization tasks, such as allocating memory
particular application action.
or opening temporary files.
Set the status variable, if necessary. The value of the
status variable becomes the filter function’s return
value.
isc_blob_filter_free InterBase ends filter processing. Perform exit tasks, such as freeing allocated memory,
Not a result of a particular closing, or removing temporary files.
application action.
isc_blob_filter_seek Reserved for internal filter use;
not used by external filters.
TABLE 8.4 Blob access operations (continued)

7,3 6WRUHUHVRXUFHSRLQWHUVVXFKDVPHPRU\SRLQWHUVDQGILOHKDQGOHVFUHDWHGE\WKH
LVFBEOREBILOWHUBRSHQKDQGOHULQWKHFWOBGDWDILHOGRIWKHLVFBEOREBFWO%OREFRQWUROVWUXFWXUH7KHQ
WKHQH[WWLPHWKHILOWHUIXQFWLRQLVFDOOHGWKHUHVRXUFHSRLQWHUVDUHVWLOODYDLODEOH

4 7HVWLQJWKHIXQFWLRQUHWXUQYDOXH
7KHILOWHUIXQFWLRQPXVWUHWXUQDQLQWHJHULQGLFDWLQJWKHVWDWXVRIWKHRSHUDWLRQLWSHUIRUPHG
<RXFDQKDYHWKHIXQFWLRQUHWXUQDQ\,QWHU%DVHVWDWXVYDOXHUHWXUQHGE\DQLQWHUQDO,QWHU%DVH
URXWLQH

188 INTERBASE 5
WRITING AN EXTERNAL BLOB FILTER

,QVRPHILOWHUDSSOLFDWLRQVDILOWHUIXQFWLRQKDVWRVXSSO\VWDWXVYDOXHVGLUHFWO\7KHIROORZLQJ
WDEOHOLVWVVWDWXVYDOXHVWKDWDSSO\SDUWLFXODUO\WR%ORESURFHVVLQJ

Macro constant Value Meaning


SUCCESS 0 Indicates the filter action has been handled successfully. On a Blob
read (isc_blob_filter_get_segment) operation, indicates that the
entire segment has been read.
FAILURE 1 Indicates an unsuccessful operation. In most cases, a status more
specific to the error is returned.
isc_uns_ext See ibase.h Indicates that the attempted action is unsupported by the filter. For
example, a read-only filter would return isc_uns_ext for an
isc_blob_filter_put_segment action.
isc_segment See ibase.h Returned during a Blob read operation. Indicates that the supplied
buffer is not large enough to contain the remaining bytes in the
current segment. In this case, only ctl_buffer_length bytes are
copied, and the remainder of the segment must be obtained through
additional isc_blob_filter_get_segment calls.
isc_segstr_eof See ibase.h Returned during a Blob read operation. Indicates that the end of the
Blob has been reached; there are no additional segments remaining
to be read.
TABLE 8.5 Blob filter status values

)RUPRUHLQIRUPDWLRQDERXW,QWHU%DVHVWDWXVYDOXHVVHHWKH/DQJXDJH5HIHUHQFH

PROGRAMMER’S GUIDE 189


CHAPTER

Chapter9 Using Arrays


9
,QWHU%DVHVXSSRUWVDUUD\VRIPRVWGDWDW\SHV8VLQJDQDUUD\HQDEOHVPXOWLSOHGDWDLWHPVWREH
VWRUHGLQDVLQJOHFROXPQ,QWHU%DVHFDQWUHDWDQDUUD\DVDVLQJOHXQLWRUDVDVHULHVRIVHSDUDWH
XQLWVFDOOHGVOLFHV8VLQJDQDUUD\LVDSSURSULDWHZKHQ
g 7KHGDWDLWHPVQDWXUDOO\IRUPDVHWRIWKHVDPHGDWDW\SH
g 7KHHQWLUHVHWRIGDWDLWHPVLQDVLQJOHGDWDEDVHFROXPQPXVWEHUHSUHVHQWHGDQGFRQWUROOHG
DVDXQLWDVRSSRVHGWRVWRULQJHDFKLWHPLQDVHSDUDWHFROXPQ
g (DFKLWHPPXVWDOVREHLGHQWLILHGDQGDFFHVVHGLQGLYLGXDOO\
7KHGDWDLWHPVLQDQDUUD\DUHFDOOHGDUUD\HOHPHQWV$QDUUD\FDQFRQWDLQHOHPHQWVRIDQ\
,QWHU%DVHGDWDW\SHH[FHSW%/2%,WFDQQRWEHDQDUUD\RIDUUD\VDOWKRXJK,QWHU%DVHGRHV
VXSSRUWPXOWLGLPHQVLRQDODUUD\V$OORIWKHHOHPHQWVRIDQDUUD\PXVWEHRIWKHVDPH
GDWDW\SH

Creating arrays
$UUD\VDUHGHILQHGZLWKWKH&5($7('20$,1RU&5($7(7$%/(VWDWHPHQWV'HILQLQJDQ
DUUD\FROXPQLVMXVWOLNHGHILQLQJDQ\RWKHUFROXPQH[FHSWWKDW\RXPXVWDOVRVSHFLI\WKH
DUUD\GLPHQVLRQV
$UUD\LQGH[HVUDQJHIURP²WR²

191
CHAPTER 9 USING ARRAYS

7KHIROORZLQJVWDWHPHQWGHILQHVDUHJXODUFKDUDFWHUFROXPQDQGDVLQJOHGLPHQVLRQFKDUDFWHU
DUUD\FROXPQFRQWDLQLQJIRXUHOHPHQWV
EXEC SQL
CREATE TABLE TABLE1
(
NAME CHAR(10),
CHAR_ARR CHAR(10)[4]
);

$UUD\GLPHQVLRQVDUHDOZD\VHQFORVHGLQVTXDUHEUDFNHWVIROORZLQJDFROXPQ·VGDWDW\SH
VSHFLILFDWLRQ
)RUDFRPSOHWHGLVFXVVLRQRI&5($7(7$%/(DQGDUUD\V\QWD[VHHWKH/DQJXDJH5HIHUHQFH

Multi-dimensional arrays
,QWHU%DVHVXSSRUWVPXOWLGLPHQVLRQDODUUD\VDUUD\VZLWKWRGLPHQVLRQV)RUH[DPSOHWKH
IROORZLQJVWDWHPHQWGHILQHVWKUHHLQWHJHUDUUD\FROXPQVZLWKWZRWKUHHDQGVL[GLPHQVLRQV
UHVSHFWLYHO\
EXEC SQL
CREATE TABLE TABLE1
(
INT_ARR2 INTEGER[4,5]
INT_ARR3 INTEGER[4,5,6]
INT_ARR6 INTEGER[4,5,6,7,8,9]
);

,QWKLVH[DPSOH,17B$55DOORFDWHVVWRUDJHIRUURZVHOHPHQWVLQZLGWKIRUDWRWDORI
LQWHJHUHOHPHQWV,17B$55DOORFDWHVHOHPHQWVDQG,17B$55DOORFDWHVHOHPHQWV

,03257$17 ,QWHU%DVHVWRUHVPXOWLGLPHQVLRQDODUUD\VLQURZPDMRURUGHU6RPHKRVWODQJXDJHVVXFKDV
)2575$1H[SHFWDUUD\VWREHLQFROXPQPDMRURUGHU,QWKHVHFDVHVFDUHPXVWEHWDNHQWR
WUDQVODWHHOHPHQWRUGHULQJFRUUHFWO\EHWZHHQ,QWHU%DVHDQGWKHKRVWODQJXDJH

Specifying subscript ranges


,Q,QWHU%DVHDUUD\GLPHQVLRQVKDYHDVSHFLILFUDQJHRIXSSHUDQGORZHUERXQGDULHVFDOOHG
VXEVFULSWV,QPDQ\FDVHVWKHVXEVFULSWUDQJHLVLPSOLFLWWKHILUVWHOHPHQWRIWKHDUUD\LV
HOHPHQWWKHVHFRQGHOHPHQWDQGWKHODVWLVHOHPHQWQ)RUH[DPSOHWKHIROORZLQJ
VWDWHPHQWFUHDWHVDWDEOHZLWKDFROXPQWKDWLVDQDUUD\RIIRXULQWHJHUV

192 INTERBASE 5
ACCESSING ARRAYS

EXEC SQL
CREATE TABLE TABLE1
(
INT_ARR INTEGER[4]
};

7KHVXEVFULSWVIRUWKLVDUUD\DUHDQG
$GLIIHUHQWVHWRIXSSHUDQGORZHUERXQGDULHVIRUHDFKDUUD\GLPHQVLRQFDQEHH[SOLFLWO\
GHILQHGZKHQDQDUUD\FROXPQLVFUHDWHG)RUH[DPSOH&SURJUDPPHUVIDPLOLDUZLWKDUUD\V
WKDWVWDUWZLWKDORZHUVXEVFULSWERXQGDU\RI]HURPD\ZDQWWRFUHDWHDUUD\FROXPQVZLWKD
ORZHUERXQGDU\RI]HURDVZHOO
7RVSHFLI\DUUD\VXEVFULSWVIRUDQDUUD\GLPHQVLRQERWKWKHORZHUDQGXSSHUERXQGDULHVRI
WKHGLPHQVLRQPXVWEHVSHFLILHGXVLQJWKHIROORZLQJV\QWD[
lower:upper

)RUH[DPSOHWKHIROORZLQJVWDWHPHQWFUHDWHVDWDEOHZLWKDVLQJOHGLPHQVLRQDUUD\FROXPQRI
IRXUHOHPHQWVZKHUHWKHORZHUERXQGDU\LVDQGWKHXSSHUERXQGDU\LV
EXEC SQL
CREATE TABLE TABLE1
(
INT_ARR INTEGER[0:3]
};

7KHVXEVFULSWVIRUWKLVDUUD\DUHDQG
:KHQFUHDWLQJPXOWLGLPHQVLRQDODUUD\VZLWKH[SOLFLWDUUD\ERXQGDULHVVHSDUDWHHDFK
GLPHQVLRQ·VVHWRIVXEVFULSWVIURPWKHQH[WZLWKFRPPDV)RUH[DPSOHWKHIROORZLQJ
VWDWHPHQWFUHDWHVDWDEOHZLWKDWZRGLPHQVLRQDODUUD\FROXPQZKHUHHDFKGLPHQVLRQKDV
IRXUHOHPHQWVZLWKERXQGDULHVRIDQG
EXEC SQL
CREATE TABLE TABLE1
(
INT_ARR INTEGER[0:3, 0:3]
};

Accessing arrays
,QWHU%DVHFDQSHUIRUPRSHUDWLRQVRQDQHQWLUHDUUD\HIIHFWLYHO\WUHDWLQJLWDVDVLQJOHHOHPHQW
RULWFDQRSHUDWHRQDQDUUD\VOLFHDVXEVHWRIDUUD\HOHPHQWV$QDUUD\VOLFHFDQFRQVLVWRID
VLQJOHHOHPHQWRUDVHWRIPDQ\FRQWLJXRXVHOHPHQWV

PROGRAMMER’S GUIDE 193


CHAPTER 9 USING ARRAYS

,QWHU%DVHVXSSRUWVWKHIROORZLQJGDWDPDQLSXODWLRQRSHUDWLRQVRQDUUD\V
g 6HOHFWLQJGDWDIURPDQDUUD\
g ,QVHUWLQJGDWDLQWRDQDUUD\
g 8SGDWLQJGDWDLQDQDUUD\VOLFH
g 6HOHFWLQJGDWDIURPDQDUUD\VOLFH
g (YDOXDWLQJDQDUUD\HOHPHQWLQDVHDUFKFRQGLWLRQ
$XVHUGHILQHGIXQFWLRQ 8') FDQRQO\UHIHUHQFHDVLQJOHDUUD\HOHPHQW
7KHIROORZLQJDUUD\RSHUDWLRQVDUHQRWVXSSRUWHG
g 5HIHUHQFLQJDUUD\GLPHQVLRQVG\QDPLFDOO\LQ'64/
g ,QVHUWLQJGDWDLQWRDQDUUD\VOLFH
g 6HWWLQJLQGLYLGXDODUUD\HOHPHQWVWR18//
g 8VLQJWKHDJJUHJDWHIXQFWLRQV0,1 0$; 680 $9* DQG&2817 ZLWKDUUD\V
g 5HIHUHQFLQJDUUD\VLQWKH*5283%<FODXVHRID6(/(&7
g &UHDWLQJYLHZVWKDWVHOHFWIURPDUUD\VOLFHV

Selecting data from an array


7RVHOHFWGDWDIURPDQDUUD\SHUIRUPWKHIROORZLQJVWHSV
 'HFODUHDKRVWODQJXDJHDUUD\YDULDEOHRIWKHFRUUHFWVL]HWRKROGWKHDUUD\GDWD
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVFUHDWHWKUHHVXFKYDULDEOHV
EXEC SQL
BEGIN DECLARE SECTION;
BASED ON TABLE1.CHAR_ARR char_arr;
BASED ON TABLE1.INT_ARR int_arr;
BASED ON TABLE1.FLOAT_ARR float_arr;
EXEC SQL
END DECLARE SECTION;

 'HFODUHDFXUVRUWKDWVSHFLILHVWKHDUUD\FROXPQVWRVHOHFW)RUH[DPSOH
EXEC SQL
DECLARE TC1 CURSOR FOR
SELECT NAME, CHAR_ARR[], INT_ARR[]
FROM TABLE1;

194 INTERBASE 5
ACCESSING ARRAYS

%HVXUHWRLQFOXGHEUDFNHWV >@ DIWHUWKHDUUD\FROXPQQDPHWRVHOHFWWKHDUUD\GDWD,IWKH


EUDFNHWVDUHOHIWRXW,QWHU%DVHUHDGVWKHDUUD\,'IRUWKHFROXPQLQVWHDGRIWKHDUUD\
GDWD
7KHDELOLW\WRUHDGWKHDUUD\,'ZKLFKLVDFWXDOO\D%ORE,'LVLQFOXGHGRQO\WRVXSSRUW
DSSOLFDWLRQVWKDWDFFHVVDUUD\GDWDXVLQJ,QWHU%DVH$3,FDOOV
 2SHQWKHFXUVRUDQGIHWFKGDWD
EXEC SQL
OPEN TC1;
EXEC SQL
FETCH TC1 INTO :name, :char_arr, :int_arr;
Note ,WLVQRWQHFHVVDU\WRXVHDFXUVRUWRVHOHFWDUUD\GDWD)RUH[DPSOHDVLQJOHWRQ6(/(&7
PLJKWEHDSSURSULDWHWRR
:KHQVHOHFWLQJDUUD\GDWDNHHSLQPLQGWKDW,QWHU%DVHVWRUHVHOHPHQWVLQURZPDMRURUGHU
)RUH[DPSOHLQDGLPHQVLRQDODUUD\ZLWKURZVDQGFROXPQVDOOHOHPHQWVLQURZDUH
UHWXUQHGWKHQDOOWKUHHHOHPHQWVLQURZWZR

Inserting data into an array


,16(57FDQEHXVHGWRLQVHUWGDWDLQWRDQDUUD\FROXPQ7KHGDWDWRLQVHUWPXVWH[DFWO\ILOO
WKHHQWLUHDUUD\RUDQHUURUFDQRFFXU
7RLQVHUWGDWDLQWRDQDUUD\IROORZWKHVHVWHSV
 'HFODUHDKRVWODQJXDJHYDULDEOHWRKROGWKHDUUD\GDWD8VHWKH%$6('21
FODXVHDVDKDQG\ZD\RIGHFODULQJDUUD\YDULDEOHVFDSDEOHRIKROGLQJGDWDWR
LQVHUWLQWRWKHHQWLUHDUUD\)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVFUHDWHWKUHH
VXFKYDULDEOHV
EXEC SQL
BEGIN DECLARE SECTION;
BASED ON TABLE1.CHAR_ARR char_arr;
BASED ON TABLE1.INT_ARR int_arr;
BASED ON TABLE1.FLOAT_ARR float_arr;
EXEC SQL
END DECLARE SECTION;

 /RDGWKHKRVWODQJXDJHYDULDEOHVZLWKGDWD
 8VH,16(57WRZULWHWKHDUUD\V)RUH[DPSOH
EXEC SQL
INSERT INTO TABLE1 (NAME, CHAR_ARR, INT_ARR, FLOAT_ARR)
VALUES ("Sample", :char_arr, :int_arr, :float_arr);

PROGRAMMER’S GUIDE 195


CHAPTER 9 USING ARRAYS

 &RPPLWWKHFKDQJHV
EXEC SQL
COMMIT;

,03257$17 :KHQLQVHUWLQJGDWDLQWRDQDUUD\FROXPQSURYLGHGDWDWRILOODOODUUD\HOHPHQWVRUWKH
UHVXOWVZLOOEHXQSUHGLFWDEOH

Selecting from an array slice


7KH6(/(&7VWDWHPHQWVXSSRUWVV\QWD[IRUUHWULHYLQJFRQWLJXRXVUDQJHVRIHOHPHQWVIURP
DUUD\V7KHVHUDQJHVDUHUHIHUUHGWRDVDUUD\VOLFHV$UUD\VOLFHVWRUHWULHYHDUHVSHFLILHGLQVTXDUH
EUDFNHWV >@ IROORZLQJDFROXPQQDPHFRQWDLQLQJDQDUUD\7KHQXPEHULQVLGHWKHEUDFNHWV
LQGLFDWHVWKHHOHPHQWVWRUHWULHYH)RUDRQHGLPHQVLRQDODUUD\WKLVLVDVLQJOHQXPEHU)RU
H[DPSOHWKHIROORZLQJVWDWHPHQWVHOHFWVWKHVHFRQGHOHPHQWLQDRQHGLPHQVLRQDODUUD\
EXEC SQL
SELECT JOB_TITLE[2]
INTO :title
FROM EMPLOYEE
WHERE LAST_NAME = :lname;

7RUHWULHYHDVXEVHWRIVHYHUDOFRQWLJXRXVHOHPHQWVIURPDRQHGLPHQVLRQDODUUD\VSHFLI\
ERWKWKHILUVWDQGODVWHOHPHQWVRIWKHUDQJHWRUHWULHYHVHSDUDWLQJWKHYDOXHVZLWKDFRORQ
7KHV\QWD[LVDVIROORZV
[lower_bound:upper_bound]
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWUHWULHYHVDVXEVHWRIWKUHHHOHPHQWVIURPD
RQHGLPHQVLRQDODUUD\
EXEC SQL
SELECT JOB_TITLE[2:4]
INTO :title
FROM EMPLOYEE
WHERE LAST_NAME = :lname;

)RUPXOWLGLPHQVLRQDODUUD\VWKHORZHUDQGXSSHUYDOXHVIRUHDFKGLPHQVLRQPXVWEH
VSHFLILHGVHSDUDWHGIURPRQHDQRWKHUE\FRPPDVXVLQJWKHIROORZLQJV\QWD[
[lower:upper, lower:upper [, lower:upper ...]]
Note ,QWKLVV\QWD[WKHEROGEUDFNHWVPXVWEHLQFOXGHG
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWUHWULHYHVWZRURZVRIWKUHHHOHPHQWVHDFK
EXEC SQL
DECLARE TC2 CURSOR FOR

196 INTERBASE 5
ACCESSING ARRAYS

SELECT INT_ARR[1:2,1:3]
FROM TABLE1

%HFDXVH,QWHU%DVHVWRUHVDUUD\GDWDLQURZPDMRURUGHUWKHILUVWUDQJHRIYDOXHVEHWZHHQWKH
EUDFNHWVVSHFLILHVWKHVXEVHWRIURZVWRUHWULHYH7KHVHFRQGUDQJHRIYDOXHVVSHFLILHVZKLFK
HOHPHQWVLQHDFKURZWRUHWULHYH
7RVHOHFWGDWDIURPDQDUUD\VOLFHSHUIRUPWKHIROORZLQJVWHSV
 'HFODUHDKRVWODQJXDJHYDULDEOHODUJHHQRXJKWRKROGWKHDUUD\VOLFHGDWD
UHWULHYHG)RUH[DPSOH
EXEC SQL
BEGIN DECLARE SECTION;
char char_slice[11]; /* 11-byte string for CHAR(10) datatype */
long int_slice[2][3];
EXEC SQL
END DECLARE SECTION;

7KHILUVWYDULDEOHFKDUBVOLFHLVLQWHQGHGWRVWRUHDVLQJOHHOHPHQWIURPWKH&+$5B$55
FROXPQ7KHVHFRQGH[DPSOHLQWBVOLFHLVLQWHQGHGWRVWRUHDVL[HOHPHQWVOLFHIURPWKH
,17B$55LQWHJHUFROXPQ
 'HFODUHDFXUVRUWKDWVSHFLILHVWKHDUUD\VOLFHVWRUHDG)RUH[DPSOH
EXEC SQL
DECLARE TC2 CURSOR FOR
SELECT CHAR_ARR[1], INT_ARR[1:2,1:3]
FROM TABLE1

 2SHQWKHFXUVRUDQGWKHIHWFKGDWD
EXEC SQL
OPEN TC2;
EXEC SQL
FETCH TC2 INTO :char_slice, :int_slice;

Updating data in an array slice


$VXEVHWRIHOHPHQWVLQDQDUUD\FDQEHXSGDWHGZLWKDFXUVRU7RSHUIRUPDQXSGDWHIROORZ
WKHVHVWHSV
 'HFODUHDKRVWODQJXDJHYDULDEOHWRKROGWKHDUUD\VOLFHGDWD)RUH[DPSOH
EXEC SQL
BEGIN DECLARE SECTION;
char char_slice[11]; /* 11-byte string for CHAR(10) datatype */
long int_slice[2][3];

PROGRAMMER’S GUIDE 197


CHAPTER 9 USING ARRAYS

EXEC SQL
END DECLARE SECTION;

7KHILUVWYDULDEOHFKDUBVOLFHLVLQWHQGHGWRKROGDVLQJOHHOHPHQWRIWKH&+$5B$55DUUD\
FROXPQGHILQHGLQWKHSURJUDPPLQJH[DPSOHLQWKHSUHYLRXVVHFWLRQ7KHVHFRQG
H[DPSOHLQWBVOLFHLVLQWHQGHGWRKROGDVL[HOHPHQWVOLFHRIWKH,17B$55LQWHJHUDUUD\
FROXPQ
 6HOHFWWKHURZWKDWFRQWDLQVWKHDUUD\GDWDWRPRGLI\)RUH[DPSOHWKHIROORZLQJ
FXUVRUGHFODUDWLRQVHOHFWVGDWDIURPWKH,17B$55$<DQG&+$5B$55$<
FROXPQV
EXEC SQL
DECLARE TC1 CURSOR FOR
SELECT CHAR_ARRAY[1], INT_ARRAY[1:2,1:3] FROM TABLE1;
EXEC SQL
OPEN TC1;
EXEC SQL
FETCH TC1 INTO :char_slice, :int_slice;

7KLVH[DPSOHIHWFKHVWKHGDWDFXUUHQWO\VWRUHGLQWKHVSHFLILHGVOLFHVRI&+$5B$55$<DQG
,17B$55$<DQGVWRUHVLWLQWRWKHFKDUBVOLFHDQGLQWBVOLFHKRVWODQJXDJHYDULDEOHV
UHVSHFWLYHO\
 /RDGWKHKRVWODQJXDJHYDULDEOHVZLWKQHZRUXSGDWHGGDWD
 ([HFXWHDQ83'$7(VWDWHPHQWWRLQVHUWGDWDLQWRWKHDUUD\VOLFHV)RUH[DPSOH
WKHIROORZLQJVWDWHPHQWVSXWGDWDLQWRSDUWVRI&+$5B$55$<DQG,17B$55$<
DVVXPLQJFKDUBVOLFHDQGLQWBVOLFHFRQWDLQLQIRUPDWLRQWRLQVHUWLQWRWKHWDEOH
EXEC SQL
UPDATE TABLE1
SET
CHAR_ARR[1] = :char_slice,
INT_ARR[1:2,1:3] = :int_slice
WHERE CURRENT OF TC1;

 &RPPLWWKHFKDQJHV
EXEC SQL
COMMIT;

7KHIROORZLQJIUDJPHQWRIWKHRXWSXWIURPWKLVH[DPSOHLOOXVWUDWHVWKHFRQWHQWVRIWKH
FROXPQV&+$5B$55DQG,17B$55DIWHUWKLVRSHUDWLRQ

198 INTERBASE 5
ACCESSING ARRAYS

char_arr values:
[0]:string0 [1]:NewString [2]:string2 [3]:string3

int_arr values:
updated values
[0][0]:0 [0][1]:1 [0][2]:2 [0][3]:3
[1][0]:10 [1][1]:999 [1][2]:999 [1][3]:999
[2][0]:20 [2][1]:999 [2][2]:999 [2][3]:999
[3][0]:30 [3][1]:31 [3][2]:32 [3][3]:33

Testing a value in a search condition


$VLQJOHDUUD\HOHPHQW·VYDOXHFDQEHHYDOXDWHGLQWKHVHDUFKFRQGLWLRQRID:+(5(FODXVH
)RUH[DPSOH
EXEC SQL
DECLARE TC2 CURSOR FOR
SELECT CHAR_ARR[1], INT_ARR[1:2,1:3]
FROM TABLE1
WHERE SMALLINT_ARR[1,1,1] = 111;

,03257$17 <RXFDQQRWHYDOXDWHPXOWLHOHPHQWDUUD\VOLFHV

Using host variables in array subscripts


,QWHJHUKRVWYDULDEOHVFDQEHXVHGDVDUUD\VXEVFULSWV)RUH[DPSOHWKHIROORZLQJFXUVRU
GHFODUDWLRQXVHVKRVWYDULDEOHVJHWYDODQGWHVWYDOLQDUUD\VXEVFULSWV
EXEC SQL
DECLARE TC2 CURSOR FOR
SELECT CHAR_ARR[1], INT_ARR[:getval:1,1:3]
FROM TABLE1
WHERE FLOAT_ARR[:testval,1,1] = 111.0;

Using arithmetic expressions with arrays


$ULWKPHWLFH[SUHVVLRQVLQYROYLQJDUUD\VFDQEHXVHGRQO\LQVHDUFKFRQGLWLRQV)RUH[DPSOH
WKHIROORZLQJFRGHIHWFKHVDURZRIDUUD\GDWDDWDWLPHWKDWPHHWVWKHVHDUFKFULWHULRQ
for (i = 1; i < 100 && SQLCODE == 0; i++)
{
EXEC SQL

PROGRAMMER’S GUIDE 199


CHAPTER 9 USING ARRAYS

SELECT ARR[:i] INTO :array_var


FROM TABLE1
WHERE ARR1[:j + 1] = 5;
process_array(array_var);
}

200 INTERBASE 5
CHAPTER

Working with Chapter10


10
User-Defined Functions

-XVWDV,QWHU%DVHKDVEXLOWLQ64/IXQFWLRQVVXFKDV0,1 0$; DQG&$67 LWDOVRVXSSRUWV


OLEUDULHVRIH[WHUQDOIXQFWLRQVRUXVHUGHILQHGIXQFWLRQV 8')V $8')LVDIXQFWLRQ
ZULWWHQHQWLUHO\LQDKRVWODQJXDJHWRSHUIRUPDGDWDPDQLSXODWLRQWDVNQRWGLUHFWO\VXSSRUWHG
E\,QWHU%DVH3RVVLELOLWLHVLQFOXGHVWDWLVWLFDOVWULQJDQGGDWHIXQFWLRQV

,03257$17 8')VDUHQRWVXSSRUWHGRQ1HW:DUH
2QFHD8')LVFUHDWHGLWFDQEHXVHGLQDGDWDEDVHDSSOLFDWLRQDQ\ZKHUHWKDWDEXLOWLQ64/
IXQFWLRQFDQEHXVHG7KLVFKDSWHUGHVFULEHVKRZWRFUHDWH8')VDQGKRZWRXVHWKHPLQDQ
DSSOLFDWLRQ

Creating a UDF
&UHDWLQJD8')LVDWKUHHVWHSSURFHVV
 :ULWLQJDQGFRPSLOLQJD8')LQDSURJUDPPLQJODQJXDJHVXFKDV&RU'HOSKL
 %XLOGLQJDG\QDPLFDOO\OLQNHGOLEUDU\FRQWDLQLQJWKH8')
 'HFODULQJWKH8')WRWKHGDWDEDVH

201
CHAPTER 10 WORKING WITH USER-DEFINED FUNCTIONS

$OOVWHSVLQWKLVSURFHVVDUHSURJUDPPLQJWDVNVH[FHSWIRUGHFODULQJD8')WRWKHGDWDEDVH
ZKLFKLVDGDWDGHILQLWLRQWDVN6WHSEXLOGLQJDG\QDPLFOLQNOLEUDU\RI8')VLVRSWLRQDO
WKRXJKKLJKO\UHFRPPHQGHG%XLOGLQJDOLEUDU\HQDEOHVWKHGDWDEDVHWROLQNWKHOLEUDU\WRDQ
DSSOLFDWLRQDWUXQWLPHZLWKRXWUHTXLULQJXVHURUSURJUDPPHULQWHUYHQWLRQ
,IDOLEUDU\LVQRWEXLOWWKHQHDFKLQGLYLGXDO8')REMHFWILOHPXVWEHPDGHVHSDUDWHO\DYDLODEOH
WRWKHGDWDEDVH

Writing and compiling functions


$8')FDQEHZULWWHQLQ&RULQDQ\RWKHUKRVWODQJXDJHWKDWFDQEHFDOOHGIURP&
7KURXJKRXWWKLVFKDSWHUWKHVDPSOH8')FRGHFRPHVIURPDVLQJOH&VRXUFHILOHXGIOLEF
ZKLFKLVLQWKH,QWHU%DVHH[DPSOHVVXEGLUHFWRU\

Writing a function module


,Q&D8')LVZULWWHQOLNHDQ\VWDQGDUGIXQFWLRQ7KH8')FDQUHTXLUHXSWRWHQLQSXW
SDUDPHWHUVDQGPXVWUHWXUQRQO\DVLQJOH&GDWDYDOXH$VLQJOHVRXUFHFRGHPRGXOHFDQ
GHILQHRQHRUPRUH8')V)RUH[DPSOHWKHVDPSOH8')PRGXOHXGIOLEFLQFOXGHVWKH
IROORZLQJ8')V
g fn_abs()UHWXUQVWKHDEVROXWHYDOXHRIDQXPEHUSDVVHGDVDQLQSXWDUJXPHQW
g fn_datediff()WDNHVWZR,QWHU%DVHGDWHVDVLQSXWDQGUHWXUQVWKHQXPEHURIGD\VEHWZHHQ
WKHP
g fn_trim() imitates the SQL-92 TRIM() function. It takesWKUHHLQSXWDUJXPHQWVDQ
LQWHJHUVSHFLI\LQJWKHVWULQJWULPRSHUDWLRQWRSHUIRUP WULPOHDGLQJFKDUDFWHUVWULPWUDLOLQJ
FKDUDFWHUVRUWULPERWKOHDGLQJDQGWUDLOLQJFKDUDFWHUV WKHFKDUDFWHUWRWULPDQGWKHVWULQJ
IURPZKLFKWRWULPFKDUDFWHUV,WUHWXUQVWKHWULPPHGVWULQJ
7KHVDPSOHFRGHIRUWKHVHIXQFWLRQVLVDVIROORZV
#include <math.h>
#include <ctype.h>
#include <string.h>
#include <time.h>

/* Defines for fn_trim(). */

#define LEADING 0
#define TRAILING 1
#define BOTH 2

202 INTERBASE 5
WRITING AND COMPILING FUNCTIONS

/* Function prototypes. */

static char *strtriml(char *string, int c);


static char *strtrimr(char *string, int c);
char *fn_trim(int operation, int c, char *string);
long fn_datediff(ISC_QUAD d1, ISC_QUAD d2);
double fn_abs(double *x);

/* Function Definitons */

/* fn_abs() returns the absolute value of its argument. */


double fn_abs( double *x)
{
return(*x < 0.0) ? -*x : *x;
}
/* fn_datediff() returns the number of days between two dates */
long fn_datediff(ISC_QUAD d1, ISC_QUAD d2)
{
struct tm tm1, tm2;

isc_decode_date(d1, &tm1); /* convert IB date to tm */


isc_decode_date(d2, &tm2);
return(long) (timelocal(&tm1) - timelocal(&tm2)) / (24 * 3600.0);
}
/* trim leading and/or trailing characters of type c from string */
char *fn_trim(int operation, int c, char *string)
{
switch (operation) {
case LEADING:
strtriml(string, c);
case TRAILING:
strtrimr(string, c);
break;
case BOTH:
default:
strtrimr(string, c);
strtriml(string, c);
break;
}
return(string);
}

PROGRAMMER’S GUIDE 203


CHAPTER 10 WORKING WITH USER-DEFINED FUNCTIONS

/* trim all chars of type c from left of string and close up */

static char *strtriml(char *string, int c)


{
int n,i;

n = 0;
while (string[n] == c) /* skip leading characters */
n++;
for (i = 0;string[n];i++,n++) /* copy backward over itself */
string[i] = string[n];
string[i] = NULL; /* don’t forget string terminator */
}
/* trim all chars of type c from right of string and truncate length */

static char *strtrimr(char *string, int c)


{
int n;

n = strlen(string) - 1;
while (string[n] == c)
n--;
string[n + 1] = NULL;
return(string);
}

$VWKLVVDPSOHFRGHLOOXVWUDWHVD8')VRXUFHFRGHPRGXOHFDQXVHW\SHGHIVGHILQHGLQWKH
,QWHU%DVHLEDVHKKHDGHUILOH7RFRPSLOHVXFKDPRGXOHVXFFHVVIXOO\LQFOXGHLEDVHKLQWKH
VRXUFHFRGHE\DGGLQJWKHIROORZLQJLQFOXGHGLUHFWLYH
#include "ibase.h"
Note 7KHVDPSOHFRGHDOVRLQFOXGHVFDOOVWRWZR,QWHU%DVHOLEUDU\IXQFWLRQV
isc_decode_date()DQGisc_encode_date()7KHLEDVHKKHDGHUILOHLQFOXGHVIXQFWLRQ
SURWRW\SHVIRUDOO,QWHU%DVHOLEUDU\IXQFWLRQFDOOV

4 6SHFLI\LQJSDUDPHWHUV
$8')FDQDFFHSWXSWRWHQSDUDPHWHUVFRUUHVSRQGLQJWRDQ\,QWHU%DVHGDWDW\SH$UUD\
HOHPHQWVFDQQRWEHSDVVHGDVSDUDPHWHUV,ID8')UHWXUQVD%OREWKHQXPEHURILQSXW
SDUDPHWHUVLVUHVWULFWHGWRQLQH$OOSDUDPHWHUVDUHSDVVHGWRWKH8')E\UHIHUHQFH
3URJUDPPLQJODQJXDJHGDWDW\SHVVSHFLILHGDVSDUDPHWHUVPXVWEHFDSDEOHRIKDQGOLQJ
FRUUHVSRQGLQJ,QWHU%DVHGDWDW\SHV)RUH[DPSOHWKH&IXQFWLRQGHFODUDWLRQIRUfn_abs()
DFFHSWVRQHSDUDPHWHURIW\SHGRXEOH7KHH[SHFWDWLRQLVWKDWZKHQfn_abs()LVFDOOHGLWZLOO
EHSDVVHGDGDWDW\SHRI'28%/(35(&,6,21E\,QWHU%DVH

204 INTERBASE 5
WRITING AND COMPILING FUNCTIONS

8')VWKDWDFFHSW%ORESDUDPHWHUVUHTXLUHVSHFLDOGDWDVWUXFWXUHIRUSURFHVVLQJ$%ORELV
SDVVHGE\UHIHUHQFHWRD%ORE8')VWUXFWXUH)RUPRUHLQIRUPDWLRQDERXWWKH%ORE8')
VWUXFWXUHVHH´:ULWLQJD%ORE8')µRQSDJH 

4 6SHFLI\LQJDUHWXUQYDOXH
$8')FDQUHWXUQYDOXHVWKDWFDQEHWUDQVODWHGLQWRDQ\,QWHU%DVHGDWDW\SHLQFOXGLQJD%ORE
EXWLWFDQQRWUHWXUQDUUD\VRIGDWDW\SHV)RUH[DPSOHWKH&IXQFWLRQGHFODUDWLRQIRUfn_abs()
UHWXUQVDYDOXHRIW\SHGRXEOHZKLFKFRUUHVSRQGVWRWKH,QWHU%DVH'28%/(35(&,6,21
GDWDW\SH
%\GHIDXOWUHWXUQYDOXHVDUHSDVVHGE\UHIHUHQFH1XPHULFYDOXHVFDQEHUHWXUQHGE\
UHIHUHQFHRUE\YDOXH7RUHWXUQDQXPHULFSDUDPHWHUE\YDOXHLQFOXGHWKHRSWLRQDO%<
9$/8(NH\ZRUGDIWHUWKHUHWXUQYDOXHZKHQGHFODULQJD8')WRDGDWDEDVH
$8')WKDWUHWXUQVD%OREGRHVQRWDFWXDOO\GHILQHDUHWXUQYDOXH,QVWHDGDSRLQWHUWRD
VWUXFWXUHGHVFULELQJWKH%OREWRUHWXUQPXVWEHSDVVHGDVWKHODVWLQSXWSDUDPHWHUWRWKH
8')
)RUPRUHLQIRUPDWLRQDERXWGHFODULQJ8')VVHH´'HFODULQJD8')WRDGDWDEDVHµRQ
SDJH )RUPRUHLQIRUPDWLRQDERXWGHFODULQJD%ORE8')VHH´'HFODULQJD%ORE8')µ
RQSDJH 

Writing a Blob UDF


$%ORE8')GLIIHUVIURPRWKHU8')VEHFDXVHSRLQWHUVWR%OREFRQWUROVWUXFWXUHVDUH
SDVVHGWRWKH8')LQVWHDGRIUHIHUHQFHVWRDFWXDOGDWD$%ORE8')FDQQRWRSHQRUFORVHD
%OREEXWLQVWHDGLQYRNHVIXQFWLRQVWRSHUIRUP%OREDFFHVV

4 &UHDWLQJD%OREFRQWUROVWUXFWXUH
$%OREFRQWUROVWUXFWXUHLVD&VWUXFWGHFODUHGZLWKLQD8')PRGXOHDVD
W\SHGHI3URJUDPPHUVPXVWSURYLGHWKHFRQWUROVWUXFWXUHGHILQLWLRQZKLFKVKRXOGEH
GHILQHGDVIROORZV
typedef struct blob {
void (*blob_get_segment) ();
int *blob_handle;
long number_segments;
long max_seglen;
long total_size;
void (*blob_put_segment) ();
} *Blob;

PROGRAMMER’S GUIDE 205


CHAPTER 10 WORKING WITH USER-DEFINED FUNCTIONS

BLOB_GET_SEGMENT
7KHILUVWILHOGLQWKH%OREVWUXFWEOREBJHWBVHJPHQWLVDSRLQWHUWRDIXQFWLRQWKDWLVFDOOHGWR
UHDGDVHJPHQWIURPD%ORELIRQHLVSDVVHGWRWKH8')7KHIXQFWLRQWDNHVIRXUDUJXPHQWV
D%OREKDQGOHWKHDGGUHVVRIDEXIIHULQWRZKLFKWRSODFH%OREDVHJPHQWRIGDWDWKDWLVUHDG
WKHVL]HRIWKDWEXIIHUDQGWKHDGGUHVVRIYDULDEOHLQWRWRVWRUHWKHVL]HRIWKHVHJPHQWWKDW
LVUHDG
,I%OREGDWDLVQRWUHDGE\WKH8')VHWEOREBJHWBVHJPHQWWR18//

BLOB_HANDLE
7KHVHFRQGILHOGLQWKH%OREVWUXFWEOREBKDQGOHLVUHTXLUHG,WLVD%OREKDQGOHWKDWXQLTXHO\
LGHQWLILHVD%ORESDVVHGWRD8')RUUHWXUQHGE\LW

NUMBER_SEGMENTS
)RU%OREGDWDSDVVHGWRD8')QXPEHUBVHJPHQWVVSHFLILHVWKHWRWDOQXPEHURIVHJPHQWVLQWKH
%ORE6HWWKLVYDOXHWR18//LI%OREGDWDLVQRWSDVVHGWRD8')

MAX_SEGLEN
)RU%OREGDWDSDVVHGWRD8')PD[BVHJOHQVSHFLILHVWKHVL]HLQE\WHVRIWKHODUJHVWVLQJOH
VHJPHQWSDVVHG6HWWKLVYDOXHWR18//LI%OREGDWDLVQRWSDVVHGWRD8')

TOTAL_SIZE
)RU%OREGDWDSDVVHGWRD8')WRWDOBVL]HVSHFLILHVWKHDFWXDOVL]HLQE\WHVRIWKH%OREDVD
VLQJOHXQLW6HWWKLVYDOXHWR18//LI%OREGDWDLVQRWSDVVHGWRD8')

BLOB_PUT_SEGMENT
7KHODVWILHOGLQWKH%OREVWUXFWEOREBSXWBVHJPHQWLVDSRLQWHUWRDIXQFWLRQWKDWLVFDOOHGWR
ZULWHDVHJPHQWWRD%ORELIRQHLVEHLQJUHWXUQHGE\WKH8')7KHIXQFWLRQWDNHVWKUHH
DUJXPHQWVD%OREKDQGOHWKHDGGUHVVRIDEXIIHUFRQWDLQLQJWKHGDWDWRZULWHLQWRWKH%ORE
DQGWKHVL]HLQE\WHVRIWKHGDWDWRZULWH
,I%OREGDWDLVQRWUHDGE\WKH8')VHWEOREBSXWBVHJPHQWWR18//

4 $%ORE8')H[DPSOH
7KHIROORZLQJFRGHFUHDWHVD8')blob_concatenate()WKDWDSSHQGVGDWDIURPRQH%ORE
WRWKHHQGRIDQRWKHU%OREWRUHWXUQDWKLUG%OREFRQVLVWLQJRIFRQFDWHQDWHG%OREGDWD
/* Blob control structure */
typedef struct blob {
void (*blob_get_segment) ();
int *blob_handle;
long number_segments;

206 INTERBASE 5
WRITING AND COMPILING FUNCTIONS

long max_seglen;
long total_size;
void (*blob_put_segment) ();
} *Blob;

extern char *isc_$alloc();


#define MAX(a, b) (a > b) ? a : b
#define DELIMITER "-----------------------------"

blob_concatenate(Blob from1, Blob from2, Blob to)


/* Note Blob to, as final input parameter, is actually for output! */
{
char *buffer;
long length, b_length;

b_length = MAX(from1->max_seglen, from2->max_seglen);


buffer = isc_alloc(b_length);

/* write the from1 Blob into the return Blob, to */


while ((*from1->blob_get_segment) (from1->blob_handle, buffer,
b_length, &length))
(*to->blob_put_segment) (to->blob_handle, buffer, length);

/* now write a delimiter as a dividing line in the blob */


(*to->blob_put_segment) (to->blob_handle, DELIMITER,
sizeof(DELIMITER) - 1);

/* finally write the from2 Blob into the return Blob, to */


while ((*from2->blob_get_segment) (from2->blob_handle, buffer,
b_length, &length))
(*to->blob_put_segment) (to->blob_handle, buffer, length);

/* free the memory allocated to the buffer */


isc_$free(buffer);
}

Compiling a function module


$IWHUD8')PRGXOHLVZULWWHQLWFDQEHFRPSLOHGLQDQRUPDOIDVKLRQLQWRREMHFWRUOLEUDU\
IRUPDW7KH8')VLQWKHUHVXOWLQJREMHFWRUOLEUDU\PRGXOHFDQWKHQEHGHFODUHGWRWKH
GDWDEDVH2QFHGHFODUHGWRWKHGDWDEDVHWKHOLEUDU\FRQWDLQLQJDOOWKH8')VLVDXWRPDWLFDOO\
ORDGHGDWUXQWLPHIURPDVKDUHGOLEUDU\RUG\QDPLFOLQNOLEUDU\

PROGRAMMER’S GUIDE 207


CHAPTER 10 WORKING WITH USER-DEFINED FUNCTIONS

,03257$17 6HHWKHPDNHILOHV PDNHILOHEFDQGPDNHILOHPVFRQ:LQWHOPDNHILOHRQ81,; LQWKH,QWHU%DVH


H[DPSOHVVXEGLUHFWRU\IRUGHWDLOVRQKRZWRFRPSLOHD8')OLEUDU\
Note 8')VDUHQRWVXSSRUWHGRQ1HW:DUH1RWDOORWKHUSODWIRUPVVXSSRUWG\QDPLFDOO\
OLQNHGRUVKDUHGOLEUDULHV2QWKHVHSODWIRUPV8')OLEUDULHVPXVWEHOLQNHGH[SOLFLWO\LQWR
DSSOLFDWLRQVRUWKH,QWHU%DVHVHUYHU

Creating a UDF library


8')OLEUDULHVDUHVWDQGDUG&REMHFWOLEUDULHVWKDWDUHG\QDPLFDOO\ORDGHGE\WKHGDWDEDVHDW
UXQWLPH8')OLEUDULHVFDQEHFUHDWHGRQDQ\SODWIRUPVXSSRUWHGE\
,QWHU%DVH7RXVHWKHVDPHVHWRI8')VZLWKGDWDEDVHVUXQQLQJRQGLIIHUHQWSODWIRUPVFUHDWH
VHSDUDWHOLEUDULHVRQHDFKSODWIRUPZKHUHWKHGDWDEDVHVUHVLGH8')VUXQRQWKHVHUYHUZKHUH
WKHGDWDEDVHUHVLGHV
7KH,QWHU%DVHH[DPSOHVGLUHFWRU\FRQWDLQVDVDPSOHPDNHILOHPDNHOLEWKDWEXLOGVD8')
IXQFWLRQOLEUDU\IURPXGIOLEFPDNHOLELVVSHFLILFWRHDFKSODWIRUPZKHUH,QWHU%DVHUXQV

Modifying a UDF library


7RDGGD8')WRDQH[LVWLQJ8')OLEUDU\RQDSODWIRUP
g &RPSLOHWKH8')DFFRUGLQJWRWKHLQVWUXFWLRQVIRUWKHSODWIRUP
g ,QFOXGHDOOREMHFWILOHVSUHYLRXVO\LQFOXGHGLQWKHOLEUDU\DQGWKHQHZO\FUHDWHGREMHFWILOHLQ
WKHFRPPDQGOLQHZKHQFUHDWLQJWKHIXQFWLRQOLEUDU\
Note 2QVRPHSODWIRUPVREMHFWILOHVFDQEHDGGHGGLUHFWO\WRH[LVWLQJOLEUDULHV)RUPRUH
LQIRUPDWLRQFRQVXOWWKHSODWIRUPVSHFLILFFRPSLOHUDQGOLQNHUGRFXPHQWDWLRQ
7RGHOHWHD8')IURPDOLEUDU\IROORZWKHOLQNHU·VLQVWUXFWLRQVIRUUHPRYLQJDQREMHFWIURP
DOLEUDU\'HOHWLQJD8')IURPDOLEUDU\GRHVQRWHOLPLQDWHUHIHUHQFHVWRLWLQWKHGDWDEDVH

Declaring a UDF to a database


$IWHUD8')LVFUHDWHGLWPXVWDOVREHGHFODUHGWRDQ\GDWDEDVHVZKHUHLWZLOOEHXVHG
'HFODULQJD8')WRDGDWDEDVHLQIRUPVWKHGDWDEDVHDERXWWKHIXQFWLRQ
g ,WVQDPHDVLWZLOOEHXVHGLQHPEHGGHG64/VWDWHPHQWV
g 7KHQXPEHUDQGGDWDW\SHVRILWVDUJXPHQWV

208 INTERBASE 5
DECLARING A UDF TO A DATABASE

g 7KHUHWXUQGDWDW\SH
g 7KHQDPHRIWKHIXQFWLRQDVLWH[LVWVLQWKH8')PRGXOHRUOLEUDU\
g 7KHQDPHRIWKHPRGXOHZKHUHWKH8')H[LVWV
7RGHFODUHD8')WRDGDWDEDVHIROORZWKHVHVWHSV
 6WDUWisqlDQGFRQQHFWWRWKHGHVLUHGGDWDEDVH
 8VHWKH'(&/$5((;7(51$/)81&7,21VWDWHPHQWWRLQIRUPWKHGDWDEDVH
DERXWWKH8')
7KHV\QWD[IRU'(&/$5((;7(51$/)81&7,21LVDVIROORZV
DECLARE EXTERNAL FUNCTION sql_name
[<datatype> | CSTRING (int) [, <datatype>] | CSTRING (int) ...]
RETURNS {<datatype> [BY VALUE] | CSTRING (int)}[FREE_IT]
ENTRY_POINT "<entryname>"
MODULE_NAME "<modulename>";

7KHIROORZLQJWDEOHGHVFULEHVWKHSDUDPHWHUVIRU'(&/$5((;7(51$/)81&7,21

Argument Description
sql_name Name of the UDF as it will appear in SQL statements.
<datatype> InterBase datatype of an input parameter. All input parameters are passed to a
UDF by reference. A UDF can have zero or more input parameters.
RETURNS Specifies the return value of a function.
PARAMETER pnum Specifies that the return value for the UDF is stored in the input parameter
identified by <pnum>.
TABLE 10.1 DECLARE EXTERNAL FUNCTION parameters

PROGRAMMER’S GUIDE 209


CHAPTER 10 WORKING WITH USER-DEFINED FUNCTIONS

Argument Description
<datatype> Specifies the InterBase SQL datatype returned by the UDF. Return values are
[BY VALUE] passed by reference unless the optional BY VALUE clause is used. Only numeric
datatypes can be returned by value.
CSTRING (int) Specifies a string value int bytes in length.
FREE_IT Frees memory of the return value after the UDF finishes running; use this
directive only if the memroy is allocated dynamically in the UDF with malloc or
similar mechanism. See the Language Reference, Chapter 5.
ENTRY_POINT Quoted string specifying the name of the UDF as stored in the linked library.
“<entryname>”
MODULE_NAME Quoted file specification identifying the library or module in which the UDF
“<modulename>” resides.
TABLE 10.1 DECLARE EXTERNAL FUNCTION parameters

VTOBQDPHLVWKHQDPHRIWKH8')WKDWLVXVHGWRFDOOWKHIXQFWLRQIURP64/VWDWHPHQWV,WFDQ
EHGLIIHUHQWIURPWKHQDPHRIWKHDFWXDOIXQFWLRQLQWKHOLEUDU\RUPRGXOHVRXUFHFRGH7KDW
QDPHPXVWEHVSHFLILHGDVHQWU\QDPH)RUH[DPSOHWKHIROORZLQJisqlVFULSWGHFODUHVWKUHH
8')V$%6 '$7(',)) DQG75,0 WRWKHHPSOR\HHJGEGDWDEDVH
CONNECT "employee.gdb";
DECLARE EXTERNAL FUNCTION ABS
DOUBLE PRECISION
RETURNS DOUBLE BY VALUE
ENTRY_POINT "fn_abs" MODULE_NAME "udflib.lib";
COMMIT;
DECLARE EXTERNAL FUNCTION DATEDIFF
DATE, DATE
RETURNS INTEGER
ENTRY_POINT "fn_datediff" MODULE_NAME "udflib.lib";
COMMIT;
DECLARE EXTERNAL FUNCTION TRIM
SMALLINT, CSTRING(256), SMALLINT
RETURNS CSTRING(256)
ENTRY_POINT "fn_trim" MODULE_NAME "udflib.lib";
COMMIT;

210 INTERBASE 5
CALLING A UDF

$OWKRXJK8')VDUHZULWWHQLQDKRVWODQJXDJHDQGWKHUHIRUHWDNHKRVWODQJXDJHGDWDW\SHVIRU
ERWKLWVSDUDPHWHUVDQGLWVUHWXUQYDOXHZKHQD8')LVGHFODUHGLWPXVWWUDQVODWHWKHPWR
64/GDWDW\SHVRUWRD&675,1*W\SHRIDVSHFLILHGPD[LPXPE\WHOHQJWK&675,1*LVXVHG
WRWUDQVODWHSDUDPHWHUVRI&+$5DQG9$5&+$5GDWDW\SHVLQWRDQXOOWHUPLQDWHG&VWULQJIRU
SURFHVVLQJDQGWRUHWXUQDYDULDEOHOHQJWKQXOOWHUPLQDWHG&VWULQJWR,QWHU%DVHIRU
DXWRPDWLFFRQYHUVLRQWR&+$5RU9$5&+$5
)RUDFRPSOHWHGLVFXVVLRQRIGHFODULQJ8')VVHHWKH'DWD'HILQLWLRQ*XLGH)RUH[DPSOHVRI
FDOOLQJ8')VIURPDQDSSOLFDWLRQLQFOXGLQJWKHXVHRI&675,1*DVDSDUDPHWHUDQGUHWXUQ
YDOXHVHH´&DOOLQJD8')µRQSDJH 

Declaring a Blob UDF


$%ORE8')LVGHFODUHGWRWKHGDWDEDVHXVLQJ'(&/$5((;7(51$/)81&7,21OLNHDQ\
QRQ%ORE8')$8')WKDWUHWXUQVD%OREGRHVQRWDFWXDOO\GHILQHDUHWXUQYDOXH,QVWHDG
DSRLQWHUWRDVWUXFWXUHGHVFULELQJWKH%OREWRUHWXUQPXVWEHSDVVHGDVWKHODVWLQSXW
SDUDPHWHUWRWKH8'))RUH[DPSOHWKHIROORZLQJVWDWHPHQWGHFODUHVWKH%ORE8')
%OREB3/86B%OREWRDGDWDEDVH
DECLARE EXTERNAL FUNCTION Blob_PLUS_Blob
Blob,
Blob,
Blob
ENTRY_POINT "blob_concatenate" MODULE_NAME "udflib.lib";
COMMIT;

Calling a UDF
$IWHUD8')LVFUHDWHGDQGGHFODUHGWRDGDWDEDVHLWFDQEHXVHGLQ64/VWDWHPHQWVZKHUHYHU
DEXLOWLQIXQFWLRQLVSHUPLWWHG7RXVHD8')LQVHUWLWVQDPHLQDQ64/VWDWHPHQWDWDQ
DSSURSULDWHORFDWLRQDQGHQFORVHLWVLQSXWDUJXPHQWVLQSDUHQWKHVHV
)RUH[DPSOHWKHIROORZLQJ'(/(7(VWDWHPHQWFDOOVWKH$%6 8')DVSDUWRIDVHDUFK
FRQGLWLRQWKDWUHVWULFWVZKLFKURZVDUHGHOHWHG
EXEC SQL
DELETE FROM CITIES
WHERE ABS (POPULATION - 100000) > 50000;
8')VFDQDOVREHFDOOHGLQVWRUHGSURFHGXUHVDQGWULJJHUV)RUPRUHLQIRUPDWLRQVHHWKH
'DWD'HILQLWLRQ*XLGH

PROGRAMMER’S GUIDE 211


CHAPTER 10 WORKING WITH USER-DEFINED FUNCTIONS

Using a UDF with SELECT


,Q6(/(&7VWDWHPHQWVD8')FDQEHXVHGLQDVHOHFWOLVWWRVSHFLI\GDWDUHWULHYDORULQWKH
:+(5(FODXVHVHDUFKFRQGLWLRQ
7KHIROORZLQJVWDWHPHQWXVHV$%6 WRJXDUDQWHHWKDWDUHWXUQHGFROXPQYDOXHLVSRVLWLYH
EXEC SQL
SELECT ABS (JOB_GRADE) FROM PROJECTS;
7KHQH[WVWDWHPHQWXVHV'$7(',)) LQDVHDUFKFRQGLWLRQWRUHVWULFWURZVUHWULHYHG
EXEC SQL
SELECT START_DATE FROM PROJECTS
WHERE DATEDIFF (:today, START_DATE) > 10;

Using a UDF with INSERT


,Q,16(57VWDWHPHQWVD8')FDQEHXVHGLQWKHFRPPDGHOLPLWHGOLVWLQWKH9$/8(6FODXVH
7KHIROORZLQJVWDWHPHQWXVHV75,0 WRUHPRYHOHDGLQJEODQNVIURPILUVWQDPHDQGWUDLOLQJ
EODQNVIURPODVWQDPHEHIRUHLQVHUWLQJWKHYDOXHVRIWKHVHKRVWYDULDEOHVLQWRWKH(03/2<((
WDEOH
EXEC SQL
INSERT INTO EMPLOYEE(FIRST_NAME, LAST_NAME, EMP_NO, DEPT_NO, SALARY)
VALUES (TRIM (0, ’ ’,:firstname), TRIM (1, ’ ’, :lastname),
:empno, :deptno, greater(30000, :est_salary));

Using a UDF with UPDATE


,Q83'$7(VWDWHPHQWVD8')FDQEHXVHGLQWKH6(7FODXVHDVSDUWRIWKHH[SUHVVLRQ
DVVLJQLQJFROXPQYDOXHV
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWXVHV75,0 WRHQVXUHWKDWXSGDWHYDOXHVGRQRWFRQWDLQ
OHDGLQJRUWUDLOLQJEODQNV
EXEC SQL
UPDATE COUNTRIES
SET COUNTRY = TRIM (2, ’ ’, COUNTRY);

212 INTERBASE 5
CALLING A UDF

Using a UDF with DELETE


,Q'(/(7(VWDWHPHQWVD8')FDQEHXVHGLQD:+(5(FODXVHVHDUFKFRQGLWLRQ
EXEC SQL
DELETE FROM COUNTRIES
WHERE ABS (POPULATION - 100000) < 50000;

PROGRAMMER’S GUIDE 213


CHAPTER

Working with
Chapter11
11
Stored Procedures

$VWRUHGSURFHGXUHLVDVHOIFRQWDLQHGVHWRIH[WHQGHG64/VWDWHPHQWVVWRUHGLQDGDWDEDVHDV
SDUWRILWVPHWDGDWD
$SSOLFDWLRQVFDQLQWHUDFWZLWKVWRUHGSURFHGXUHVLQWKHIROORZLQJZD\V
g 7KH\FDQSDVVSDUDPHWHUVWRDQGUHFHLYHUHWXUQYDOXHVIURPVWRUHGSURFHGXUHV
g 7KH\FDQLQYRNHVWRUHGSURFHGXUHVGLUHFWO\WRSHUIRUPDWDVN
g 7KH\FDQVXEVWLWXWHDQDSSURSULDWHVWRUHGSURFHGXUHIRUDWDEOHRUYLHZLQD6(/(&7
VWDWHPHQW
7KHDGYDQWDJHVRIXVLQJVWRUHGSURFHGXUHVDUH
g $SSOLFDWLRQVFDQVKDUHFRGH$FRPPRQSLHFHRI64/FRGHZULWWHQRQFHDQGVWRUHGLQWKH
GDWDEDVHFDQEHXVHGLQDQ\DSSOLFDWLRQWKDWDFFHVVHVWKHGDWDEDVHLQFOXGLQJWKHQHZ
,QWHU%DVHLQWHUDFWLYH64/WRROisql
g 0RGXODUGHVLJQ6WRUHGSURFHGXUHVFDQEHVKDUHGDPRQJDSSOLFDWLRQVHOLPLQDWLQJGXSOLFDWH
FRGHDQGUHGXFLQJWKHVL]HRIDSSOLFDWLRQV
g 6WUHDPOLQHGPDLQWHQDQFH:KHQDSURFHGXUHLVXSGDWHGWKHFKDQJHVDUHDXWRPDWLFDOO\
UHIOHFWHGLQDOODSSOLFDWLRQVWKDWXVHLWZLWKRXWWKHQHHGWRUHFRPSLOHDQGUHOLQNWKHP

215
CHAPTER 11 WORKING WITH STORED PROCEDURES

g ,PSURYHGSHUIRUPDQFHHVSHFLDOO\IRUUHPRWHFOLHQWDFFHVV6WRUHGSURFHGXUHVDUHH[HFXWHG
E\WKHVHUYHUQRWWKHFOLHQW
7KLVFKDSWHUGHVFULEHVKRZWRFDOODQGH[HFXWHVWRUHGSURFHGXUHVLQDSSOLFDWLRQVRQFHWKH\
DUHZULWWHQ)RULQIRUPDWLRQRQKRZWRFUHDWHDVWRUHGSURFHGXUHVHHWKH'DWD'HILQLWLRQ
*XLGH

Using stored procedures


7KHUHDUHWZRW\SHVRISURFHGXUHVWKDWFDQEHFDOOHGIURPDQDSSOLFDWLRQ
g 6HOHFWSURFHGXUHVWKDWDQDSSOLFDWLRQFDQXVHLQSODFHRIDWDEOHRUYLHZLQD6(/(&7VWDWHPHQW
$VHOHFWSURFHGXUHPXVWUHWXUQRQHRUPRUHYDOXHVRUDQHUURUUHVXOWV
g ([HFXWDEOHSURFHGXUHVWKDWDQDSSOLFDWLRQFDQFDOOGLUHFWO\ZLWKWKH(;(&87(352&('85(
VWDWHPHQW$QH[HFXWDEOHSURFHGXUHPD\RUPD\QRWUHWXUQYDOXHVWRWKHFDOOLQJSURJUDP
%RWKNLQGVRISURFHGXUHVDUHGHILQHGZLWK&5($7(352&('85(DQGKDYHWKHVDPHV\QWD[
7KHGLIIHUHQFHLVLQKRZWKHSURFHGXUHLVZULWWHQDQGKRZLWLVLQWHQGHGWREHXVHG6HOHFW
SURFHGXUHVDOZD\VUHWXUQ]HURRUPRUHURZVVRWKDWWRWKHFDOOLQJSURJUDPWKH\DSSHDUDVD
WDEOHRUYLHZ([HFXWDEOHSURFHGXUHVDUHVLPSO\URXWLQHVLQYRNHGE\WKHFDOOLQJSURJUDPWKDW
FDQUHWXUQRQO\DVLQJOHVHWRIYDOXHV
,QIDFWDVLQJOHSURFHGXUHFRQFHLYDEO\FDQEHXVHGDVDVHOHFWSURFHGXUHRUDQH[HFXWDEOH
SURFHGXUHEXWWKLVLVQRWUHFRPPHQGHG,QJHQHUDODSURFHGXUHLVZULWWHQVSHFLILFDOO\WREH
XVHGLQD6(/(&7VWDWHPHQW DVHOHFWSURFHGXUH RUWREHXVHGLQDQ(;(&87(352&('85(
VWDWHPHQW DQH[HFXWDEOHSURFHGXUH )RUPRUHLQIRUPDWLRQRQFUHDWLQJVWRUHGSURFHGXUHV
VHHWKH'DWD'HILQLWLRQ*XLGH

Procedures and transactions


3URFHGXUHVRSHUDWHZLWKLQWKHFRQWH[WRIDWUDQVDFWLRQLQWKHSURJUDPWKDWXVHVWKHP,I
SURFHGXUHVDUHXVHGLQDWUDQVDFWLRQDQGWKHWUDQVDFWLRQLVUROOHGEDFNWKHQDQ\DFWLRQV
SHUIRUPHGE\WKHSURFHGXUHVDUHDOVRUROOHGEDFN6LPLODUO\DSURFHGXUH·VDFWLRQVDUHQRWILQDO
XQWLOLWVFRQWUROOLQJWUDQVDFWLRQLVFRPPLWWHG

216 INTERBASE 5
USING SELECT PROCEDURES

Security for procedures


:KHQDQDSSOLFDWLRQFDOOVDVWRUHGSURFHGXUHWKHSHUVRQUXQQLQJWKHDSSOLFDWLRQPXVWKDYH
(;(&87(SULYLOHJHRQWKHVWRUHGSURFHGXUH$QH[WHQVLRQWRWKH*5$17VWDWHPHQWHQDEOHV
DVVLJQPHQWRI(;(&87(SULYLOHJHDQGDQH[WHQVLRQWRWKH5(92.(VWDWHPHQWHQDEOHV
UHPRYDORIWKHSULYLOHJH)RUPRUHLQIRUPDWLRQDERXWJUDQWLQJSULYLOHJHVWRXVHUVVHHWKH
'DWD'HILQLWLRQ*XLGH
,QDGGLWLRQLIWKHVWRUHGSURFHGXUHDFFHVVHVREMHFWVLQWKHGDWDEDVHRQHRIWZRWKLQJVPXVW
EHWUXHHLWKHUWKHXVHUUXQQLQJWKHDSSOLFDWLRQRUWKHFDOOHGVWRUHGSURFHGXUHPXVWKDYHWKH
DSSURSULDWHSHUPLVVLRQVRQWKHDFFHVVHGREMHFWV7KH*5$17VWDWHPHQWDVVLJQVSULYLOHJHVWR
SURFHGXUHVDQG5(92.(HOLPLQDWHVSULYLOHJHV

Using select procedures


$VHOHFWSURFHGXUHLVXVHGLQSODFHRIDWDEOHRUYLHZLQD6(/(&7VWDWHPHQWDQGFDQUHWXUQ
]HURRUPRUHURZV$VHOHFWSURFHGXUHPXVWUHWXUQRQHRUPRUHRXWSXWSDUDPHWHUVRUDQ
HUURUUHVXOWV,IUHWXUQHGYDOXHVDUHQRWVSHFLILHG18//YDOXHVDUHUHWXUQHGE\GHIDXOW
7KHDGYDQWDJHVRIVHOHFWSURFHGXUHVRYHUWDEOHVRUYLHZVDUH
g 7KH\FDQWDNHLQSXWSDUDPHWHUVWKDWFDQDIIHFWWKHRXWSXWSURGXFHG
g 7KH\FDQFRQWDLQFRQWUROVWDWHPHQWVORFDOYDULDEOHVDQGGDWDPDQLSXODWLRQVWDWHPHQWV
RIIHULQJJUHDWIOH[LELOLW\WRWKHXVHU
,QSXWSDUDPHWHUVDUHSDVVHGWRDVHOHFWSURFHGXUHLQDFRPPDGHOLPLWHGOLVWLQSDUHQWKHVHV
IROORZLQJWKHSURFHGXUHQDPH
7KHIROORZLQJisqlVFULSWGHILQHVWKHSURFHGXUH*(7B(03B352-ZKLFKUHWXUQVHPSBSURMWKH
SURMHFWQXPEHUVDVVLJQHGWRDQHPSOR\HHZKHQSDVVHGWKHHPSOR\HHQXPEHUHPSBQRDVWKH
LQSXWSDUDPHWHU
SET TERM !! ;
CREATE PROCEDURE GET_EMP_PROJ (emp_no SMALLINT)
RETURNS (emp_proj SMALLINT) AS
BEGIN
FOR SELECT PROJ_ID
FROM EMPLOYEE_PROJECT
WHERE EMP_NO = :emp_no
INTO :emp_proj
DO

PROGRAMMER’S GUIDE 217


CHAPTER 11 WORKING WITH STORED PROCEDURES

SUSPEND;
END !!

7KHIROORZLQJVWDWHPHQWUHWULHYHV352-B,'IURPWKHDERYHSURFHGXUHSDVVLQJWKHKRVW
YDULDEOHQXPEHUDVLQSXW
SELECT PROJ_ID FROM GET_EMP_PROJ (:number);

Calling a select procedure


7RXVHDVHOHFWSURFHGXUHLQSODFHRIDWDEOHRUYLHZQDPHLQDQDSSOLFDWLRQXVHWKHSURFHGXUH
QDPHDQ\ZKHUHDWDEOHRUYLHZQDPHLVDSSURSULDWH6XSSO\DQ\LQSXWSDUDPHWHUVUHTXLUHGLQ
DFRPPDGHOLPLWHGOLVWLQSDUHQWKHVHVIROORZLQJWKHSURFHGXUHQDPH
EXEC SQL
SELECT PROJ_ID FROM GET_EMP_PROJ (:emp_no)
ORDER BY PROJ_ID;

,03257$17 ,QWHU%DVHGRHVQRWVXSSRUWFUHDWLQJDYLHZE\FDOOLQJDVHOHFWSURFHGXUH

Using a select procedure with cursors


$VHOHFWSURFHGXUHFDQDOVREHXVHGLQDFXUVRUGHFODUDWLRQ)RUH[DPSOHWKHIROORZLQJFRGH
GHFODUHVDFXUVRUQDPHG352-(&76XVLQJWKH*(7B(03B352-SURFHGXUHLQSODFHRIDWDEOH
EXEC SQL
DECLARE PROJECTS CURSOR FOR
SELECT PROJ_ID FROM GET_EMP_PROJ (:emp_no)
ORDER BY PROJ_ID;

7KHIROORZLQJDSSOLFDWLRQ&FRGHZLWKHPEHGGHG64/WKHQXVHVWKH352-(&76FXUVRUWR
SULQWSURMHFWQXPEHUVWRVWDQGDUGRXWSXW
EXEC SQL
OPEN PROJECTS

/* Print employee projects. */


while (SQLCODE == 0)
{
EXEC SQL
FETCH PROJECTS INTO :proj_id :nullind;
if (SQLCODE == 100)
break;
if (nullind == 0)

218 INTERBASE 5
USING EXECUTABLE PROCEDURES

printf("\t%s\n", proj_id);
}

Using executable procedures


$QH[HFXWDEOHSURFHGXUHLVFDOOHGGLUHFWO\E\DQDSSOLFDWLRQDQGRIWHQSHUIRUPVDWDVN
FRPPRQWRDSSOLFDWLRQVXVLQJWKHVDPHGDWDEDVH([HFXWDEOHSURFHGXUHVFDQUHFHLYHLQSXW
SDUDPHWHUVIURPWKHFDOOLQJSURJUDPDQGFDQRSWLRQDOO\UHWXUQDVLQJOHURZWRWKHFDOOLQJ
SURJUDP
,QSXWSDUDPHWHUVSDVVWRDQH[HFXWDEOHSURFHGXUHLQDFRPPDGHOLPLWHGOLVWIROORZLQJWKH
SURFHGXUHQDPH
Note ([HFXWDEOHSURFHGXUHVFDQQRWUHWXUQPXOWLSOHURZV

Executing a procedure
7RH[HFXWHDSURFHGXUHLQDQDSSOLFDWLRQXVHWKHIROORZLQJV\QWD[
EXEC SQL
EXECUTE PROCEDURE name [:param [[INDICATOR]:indicator]]
[, :param [[INDICATOR]:indicator] ...]
[RETURNING_VALUES :param [[INDICATOR]:indicator]
[, :param [[INDICATOR]:indicator]...]];

:KHQDQH[HFXWDEOHSURFHGXUHXVHVLQSXWSDUDPHWHUVWKHSDUDPHWHUVFDQEHOLWHUDOYDOXHV
VXFKDVRU´)UHGµ RUKRVWYDULDEOHV,IDSURFHGXUHUHWXUQVRXWSXWSDUDPHWHUVKRVW
YDULDEOHVPXVWEHVXSSOLHGLQWKH5(7851,1*B9$/8(6FODXVHWRKROGWKHYDOXHVUHWXUQHG
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWGHPRQVWUDWHVKRZWKHH[HFXWDEOHSURFHGXUH
'(37B%8'*(7LVFDOOHGZLWKOLWHUDOSDUDPHWHUV
EXEC SQL
EXECUTE PROCEDURE DEPT_BUDGET 100 RETURNING_VALUES :sumb;

7KHIROORZLQJVWDWHPHQWDOVRFDOOVWKHVDPHSURFHGXUHXVLQJDKRVWYDULDEOHLQVWHDGRIDOLWHUDO
DVWKHLQSXWSDUDPHWHU
EXEC SQL
EXECUTE PROCEDURE DEPT_BUDGET :rdno RETURNING_VALUES :sumb;

PROGRAMMER’S GUIDE 219


CHAPTER 11 WORKING WITH STORED PROCEDURES

4 ,QGLFDWRUYDULDEOHV
%RWKLQSXWSDUDPHWHUVDQGUHWXUQYDOXHVFDQKDYHDVVRFLDWHGLQGLFDWRUYDULDEOHVIRUWUDFNLQJ
18//YDOXHV<RXPXVWXVHLQGLFDWRUYDULDEOHVWRLQGLFDWHXQNQRZQRU18//YDOXHVRIUHWXUQ
SDUDPHWHUV7KH,1',&$725NH\ZRUGLVRSWLRQDO$QLQGLFDWRUYDULDEOHWKDWLVOHVVWKDQ]HUR
LQGLFDWHVWKDWWKHSDUDPHWHULVXQNQRZQRU18//$QLQGLFDWRUYDULDEOHWKDWLVLQGLFDWHVWKDW
WKHDVVRFLDWHGSDUDPHWHUFRQWDLQVDQRQ18//YDOXH)RUPRUHLQIRUPDWLRQDERXWLQGLFDWRU
YDULDEOHVVHH&KDSWHU´:RUNLQJZLWK'DWDµ

Executing a procedure in a DSQL application


7RH[HFXWHDVWRUHGSURFHGXUHLQDG\QDPLF64/ '64/ DSSOLFDWLRQIROORZWKHVHVWHSV
 8VHD35(3$5(VWDWHPHQWWRSDUVHDQGSUHSDUHWKHSURFHGXUHFDOOIRUH[HFXWLRQ
XVLQJWKHIROORZLQJV\QWD[
EXEC SQL
PREPARE sql_statement_name FROM :var | "<statement>";

 6HWXSDQLQSXW;64/'$XVLQJWKHIROORZLQJV\QWD[
EXEC SQL
DESCRIBE INPUT sql_statement_name INTO SQL DESCRIPTOR input_xsqlda;

 8VH'(6&5,%(287387WRVHWXSDQRXWSXW;64/'$XVLQJWKHIROORZLQJV\QWD[
EXEC SQL
DESCRIBE OUTPUT sql_statement_name INTO SQL DESCRIPTOR
output_xsqlda;
6HWWLQJXSDQRXWSXW;64/'$LVRQO\QHFHVVDU\IRUSURFHGXUHVWKDWUHWXUQYDOXHV
 ([HFXWHWKHVWDWHPHQWXVLQJWKHIROORZLQJV\QWD[
EXEC SQL
EXECUTE statement USING SQL DESCRIPTOR input_xsqlda
INTO DESCRIPTOR output_xsqlda;

,QSXWSDUDPHWHUVWRVWRUHGSURFHGXUHVFDQEHSDVVHGDVUXQWLPHYDOXHVE\VXEVWLWXWLQJD
TXHVWLRQPDUN " IRUHDFKYDOXH)RUH[DPSOHWKHIROORZLQJ'64/VWDWHPHQWVSUHSDUHDQG
H[HFXWHWKH$''B(03B352-SURFHGXUH
. . .
strcpy(uquery, "EXECUTE PROCEDURE ADD_EMP_PROJ ?, ?");
. . .
EXEC SQL
PREPARE QUERY FROM :uquery;
EXEC SQL

220 INTERBASE 5
USING EXECUTABLE PROCEDURES

DESCRIBE INPUT QUERY INTO SQL DESCRIPTOR input_xsqlda;


EXEC SQL
DESCRIBE OUTPUT QUERY INTO SQL DESCRIPTOR output_xsqlda;
EXEC SQL
EXECUTE QUERY USING SQL DESCRIPTOR input_xsqlda INTO SQL DESCRIPTOR
output_xsqlda;
. . .

PROGRAMMER’S GUIDE 221


CHAPTER

Working with Events


Chapter12
12
7KLVFKDSWHUGHVFULEHVWKH,QWHU%DVHHYHQWPHFKDQLVPDQGKRZWRZULWHDSSOLFDWLRQVWKDW
UHJLVWHULQWHUHVWLQDQGUHVSRQGWRHYHQWV7KHHYHQWPHFKDQLVPHQDEOHVDSSOLFDWLRQVWR
UHVSRQGWRDFWLRQVDQGGDWDEDVHFKDQJHVPDGHE\RWKHUFRQFXUUHQWO\UXQQLQJDSSOLFDWLRQV
ZLWKRXWWKHQHHGIRUWKRVHDSSOLFDWLRQVWRFRPPXQLFDWHGLUHFWO\ZLWKRQHDQRWKHUDQG
ZLWKRXWLQFXUULQJWKHH[SHQVHRI&38WLPHUHTXLUHGIRUSHULRGLFSROOLQJWRGHWHUPLQHLIDQ
HYHQWKDVRFFXUUHG

Understanding the event mechanism


,Q,QWHU%DVHDQHYHQWLVDPHVVDJHSDVVHGE\DWULJJHURUDVWRUHGSURFHGXUHWRWKH,QWHU%DVH
HYHQWPDQDJHUWRDQQRXQFHWKHRFFXUUHQFHRIDVSHFLILHGFRQGLWLRQRUDFWLRQXVXDOO\D
GDWDEDVHFKDQJHVXFKDVDQ,16(5783'$7(RU'(/(7((YHQWVDUHSDVVHGE\WULJJHUVRU
VWRUHGSURFHGXUHVRQO\ZKHQWKHWUDQVDFWLRQXQGHUZKLFKWKH\RFFXULVFRPPLWWHG
7KHHYHQWPDQDJHUPDLQWDLQVDOLVWRIHYHQWVSRVWHGWRLWE\WULJJHUVDQGVWRUHGSURFHGXUHV,W
DOVRPDLQWDLQVDOLVWRIDSSOLFDWLRQVWKDWKDYHUHJLVWHUHGDQLQWHUHVWLQHYHQWV(DFKWLPHDQHZ
HYHQWLVSRVWHGWRLWWKHHYHQWPDQDJHUQRWLILHVLQWHUHVWHGDSSOLFDWLRQVWKDWWKHHYHQWKDV
RFFXUUHG
$SSOLFDWLRQVFDQUHVSRQGWRVSHFLILFHYHQWVWKDWPLJKWEHSRVWHGE\DWULJJHURUVWRUHG
SURFHGXUHE\

223
CHAPTER 12 WORKING WITH EVENTS

 ,QGLFDWLQJDQLQWHUHVWLQWKHHYHQWVWRWKHHYHQWPDQDJHU
 :DLWLQJIRUHYHQWQRWLILFDWLRQ
 'HWHUPLQLQJZKLFKHYHQWRFFXUUHG LIDQDSSOLFDWLRQLVZDLWLQJIRUPRUHWKDQ
RQHHYHQWWRRFFXU 
7KH,QWHU%DVHHYHQWPHFKDQLVPWKHQFRQVLVWVRIWKUHHSDUWV
g $WULJJHURUVWRUHGSURFHGXUHWKDWSRVWVDQHYHQWWRWKHHYHQWPDQDJHU
g 7KHHYHQWPDQDJHUWKDWPDLQWDLQVDQHYHQWTXHXHDQGQRWLILHVDSSOLFDWLRQVZKHQDQHYHQW
RFFXUV
g $QDSSOLFDWLRQWKDWUHJLVWHUVLQWHUHVWLQWKHHYHQWDQGZDLWVIRULWWRRFFXU
$VHFRQGDSSOLFDWLRQWKDWXVHVWKHHYHQWSRVWLQJVWRUHGSURFHGXUH RUWKDWILUHVWKHWULJJHU 
FDXVHVWKHHYHQWPDQDJHUWRQRWLI\WKHZDLWLQJDSSOLFDWLRQVRWKDWLWFDQUHVXPHSURFHVVLQJ

Signaling event occurrences


$WULJJHURUVWRUHGSURFHGXUHPXVWVLJQDOWKHRFFXUUHQFHRIDQHYHQWXVXDOO\DGDWDEDVH
FKDQJHVXFKDVDQ,16(5783'$7(RU'(/(7(E\XVLQJWKH3267B(9(17VWDWHPHQW
3267B(9(17DOHUWVWKHHYHQWPDQDJHUWRWKHRFFXUUHQFHRIDQHYHQWDIWHUDWUDQVDFWLRQLV
FRPPLWWHG$WWKDWWLPHWKHHYHQWPDQDJHUSDVVHVWKHLQIRUPDWLRQWRUHJLVWHUHGDSSOLFDWLRQV
$WULJJHURUVWRUHGSURFHGXUHWKDWSRVWVDQHYHQWLVVRPHWLPHVFDOOHGDQHYHQWDOHUWHU)RU
H[DPSOHWKHIROORZLQJisqlVFULSWFUHDWHVDWULJJHUWKDWSRVWVDQHYHQWWRWKHHYHQWPDQDJHU
ZKHQHYHUDQ\DSSOLFDWLRQLQVHUWVGDWDLQDWDEOH
SET TERM !! ;
CREATE TRIGGER POST_NEW_ORDER FOR SALES
ACTIVE
AFTER INSERT
POSITION 0
AS
BEGIN
POST_EVENT "new_order";
END
!!
SET TERM ; !!
(YHQWQDPHVDUHUHVWULFWHGWRFKDUDFWHUVLQVL]H
Note 3267B(9(17LVDVWRUHGSURFHGXUHDQGWULJJHUODQJXDJHH[WHQVLRQDYDLODEOHRQO\
ZLWKLQVWRUHGSURFHGXUHVDQGWULJJHUV

224 INTERBASE 5
REGISTERING INTEREST IN EVENTS

)RUDFRPSOHWHGLVFXVVLRQRIZULWLQJDWULJJHURUVWRUHGSURFHGXUHDVDQHYHQWDOHUWHUVHHWKH
'DWD'HILQLWLRQ*XLGH

Registering interest in events


$QDSSOLFDWLRQPXVWUHJLVWHUDUHTXHVWWREHQRWLILHGDERXWDSDUWLFXODUHYHQWZLWKWKH
,QWHU%DVHHYHQWPDQDJHUEHIRUHZDLWLQJIRUWKHHYHQWWRRFFXU7RUHJLVWHULQWHUHVWLQDQ
HYHQWXVHWKH(9(17,1,7VWDWHPHQW(9(17,1,7UHTXLUHVWZRDUJXPHQWV
g $QDSSOLFDWLRQVSHFLILFUHTXHVWKDQGOHWRSDVVWRWKHHYHQWPDQDJHU
g $OLVWRIHYHQWVWREHQRWLILHGDERXWHQFORVHGLQSDUHQWKHVHV
7KHDSSOLFDWLRQVSHFLILFUHTXHVWKDQGOHLVXVHGE\WKHDSSOLFDWLRQLQDVXEVHTXHQW(9(17
:$,7VWDWHPHQWWRLQGLFDWHDUHDGLQHVVWRUHFHLYHHYHQWQRWLILFDWLRQ7KHUHTXHVWKDQGOHLV
XVHGE\WKHHYHQWPDQDJHUWRGHWHUPLQHZKHUHWRVHQGQRWLILFDWLRQDERXWSDUWLFXODUHYHQWV
WRZDNHXSDVOHHSLQJDSSOLFDWLRQVRWKDWLWFDQUHVSRQGWRWKHP
7KHOLVWRIHYHQWQDPHVLQSDUHQWKHVHVPXVWPDWFKHYHQWQDPHVSRVWHGE\WULJJHUVRUVWRUHG
SURFHGXUHVRUQRWLILFDWLRQFDQQRWRFFXU
7RUHJLVWHULQWHUHVWLQDVLQJOHHYHQWXVHWKHIROORZLQJ(9(17,1,7V\QWD[
EXEC SQL
EVENT INIT request_name (event_name);

HYHQWBQDPHFDQEHXSWRFKDUDFWHUVLQVL]HDQGFDQEHSDVVHGDVDFRQVWDQWVWULQJLQTXRWHV
RUDVDKRVWODQJXDJHYDULDEOH
)RUH[DPSOHWKHIROORZLQJDSSOLFDWLRQFRGHFUHDWHVDUHTXHVWQDPHG5(6321'B1(:WKDW
UHJLVWHUVLQWHUHVWLQWKH´QHZBRUGHUµHYHQW
EXEC SQL
EVENT INIT RESPOND_NEW ("new_order");

7KHQH[WH[DPSOHLOOXVWUDWHVKRZ5(6321'B1(:PLJKWEHLQLWLDOL]HGXVLQJDKRVWODQJXDJH
YDULDEOHP\HYHQWWRVSHFLI\WKHQDPHRIDQHYHQW
EXEC SQL
EVENT INIT RESPOND_NEW (:myevent);

$IWHUDQDSSOLFDWLRQUHJLVWHUVLQWHUHVWLQDQHYHQWLWLVQRWQRWLILHGDERXWDQHYHQWXQWLOLWILUVW
SDXVHVH[HFXWLRQZLWK(9(17:$,7)RUPRUHLQIRUPDWLRQDERXWZDLWLQJIRUHYHQWVVHH
´:DLWLQJIRUHYHQWVZLWK(9(17:$,7µRQSDJH 

PROGRAMMER’S GUIDE 225


CHAPTER 12 WORKING WITH EVENTS

Note $VDQDOWHUQDWLYHWRUHJLVWHULQJLQWHUHVWLQDQHYHQWDQGZDLWLQJIRUWKHHYHQWWRRFFXU
DSSOLFDWLRQVFDQXVHDQ,QWHU%DVH$3,FDOOWRUHJLVWHULQWHUHVWLQDQHYHQWDQGLGHQWLI\DQ
DV\QFKURQRXVWUDS $67 IXQFWLRQWRUHFHLYHHYHQWQRWLILFDWLRQ7KLVPHWKRGHQDEOHVDQ
DSSOLFDWLRQWRFRQWLQXHRWKHUSURFHVVLQJLQVWHDGRIZDLWLQJIRUDQHYHQWWRRFFXU)RUPRUH
LQIRUPDWLRQDERXWSURJUDPPLQJHYHQWVZLWKWKH,QWHU%DVH$3,VHHWKH$3,*XLGH

Registering interest in multiple events


2IWHQDQDSSOLFDWLRQPD\EHLQWHUHVWHGLQVHYHUDOGLIIHUHQWHYHQWVHYHQWKRXJKLWFDQRQO\
ZDLWRQDVLQJOHUHTXHVWKDQGOHDWDWLPH(9(17,1,7HQDEOHVDQDSSOLFDWLRQWRVSHFLI\DOLVW
RIHYHQWQDPHVLQSDUHQWKHVHVXVLQJWKHIROORZLQJV\QWD[
EXEC SQL
EVENT INIT request_name (event_name [event_name ...]);

(DFKHYHQWBQDPHFDQEHXSWRFKDUDFWHUVLQVL]HDQGVKRXOGFRUUHVSRQGWRHYHQWQDPHV
SRVWHGE\WULJJHUVRUVWRUHGSURFHGXUHVRUQRWLILFDWLRQPD\QHYHURFFXU)RUH[DPSOHWKH
IROORZLQJDSSOLFDWLRQFRGHFUHDWHVDUHTXHVWQDPHG5(6321'B0$1<WKDWUHJLVWHUVLQWHUHVW
LQWKUHHHYHQWV´QHZBRUGHUµ´FKDQJHBRUGHUµDQG´FDQFHOBRUGHUµ
EXEC SQL
EVENT INIT RESPOND_MANY ("new_order", "change_order",
"cancel_order");

Note $QDSSOLFDWLRQFDQDOVRUHJLVWHULQWHUHVWLQPXOWLSOHHYHQWVE\XVLQJDVHSDUDWH(9(17
,1,7VWDWHPHQWZLWKDXQLTXHUHTXHVWKDQGOHIRUDVLQJOHHYHQWRUJURXSVRIHYHQWVEXWLWFDQ
RQO\ZDLWRQRQHUHTXHVWKDQGOHDWDWLPH

Waiting for events with EVENT WAIT


(YHQDIWHUDQDSSOLFDWLRQUHJLVWHUVLQWHUHVWLQDQHYHQWLWGRHVQRWUHFHLYHQRWLILFDWLRQDERXW
WKDWHYHQW%HIRUHLWFDQUHFHLYHQRWLILFDWLRQLWPXVWXVHWKH(9(17:$,7VWDWHPHQWWR
LQGLFDWHLWVUHDGLQHVVWRWKHHYHQWPDQDJHUDQGWRVXVSHQGLWVSURFHVVLQJXQWLOQRWLILFDWLRQ
RFFXUV
7RVLJQDOWKHHYHQWPDQDJHUDQGVXVSHQGDQDSSOLFDWLRQ·VSURFHVVLQJXVHWKHIROORZLQJ
(9(17:$,7VWDWHPHQWV\QWD[
EXEC SQL
EVENT WAIT request_name;

226 INTERBASE 5
RESPONDING TO EVENTS

UHTXHVWBQDPHPXVWEHWKHQDPHRIDUHTXHVWKDQGOHGHFODUHGLQDSUHYLRXV(9(17,1,7
VWDWHPHQW
7KHIROORZLQJVWDWHPHQWVUHJLVWHULQWHUHVWLQDQHYHQWDQGZDLWIRUHYHQWQRWLILFDWLRQ
EXEC SQL
EVENT INIT RESPOND_NEW ("new_order");
EXEC SQL
EVENT WAIT RESPOND_NEW;

2QFH(9(17:$,7LVH[HFXWHGDSSOLFDWLRQSURFHVVLQJVWRSVXQWLOWKHHYHQWPDQDJHUVHQGV
DQRWLILFDWLRQPHVVDJHWRWKHDSSOLFDWLRQ
Note $QDSSOLFDWLRQFDQFRQWDLQPRUHWKDQRQH(9(17:$,7VWDWHPHQWEXWDOOSURFHVVLQJ
VWRSVZKHQWKHILUVWVWDWHPHQWLVHQFRXQWHUHG(DFKWLPHSURFHVVLQJUHVWDUWVLWVWRSVZKHQLW
HQFRXQWHUVWKHQH[W(9(17:$,7VWDWHPHQW
,IRQHHYHQWRFFXUVZKLOHDQDSSOLFDWLRQLVSURFHVVLQJDQRWKHUWKHHYHQWPDQDJHUVHQGV
QRWLILFDWLRQWKHQH[WWLPHWKHDSSOLFDWLRQUHWXUQVWRDZDLWVWDWH

Responding to events
:KHQHYHQWQRWLILFDWLRQRFFXUVDVXVSHQGHGDSSOLFDWLRQUHVXPHVQRUPDOSURFHVVLQJDWWKH
QH[WVWDWHPHQWIROORZLQJ(9(17:$,7
,IDQDSSOLFDWLRQKDVUHJLVWHUHGLQWHUHVWLQPRUHWKDQRQHHYHQWZLWKDVLQJOH(9(17,1,7FDOO
WKHQWKHDSSOLFDWLRQPXVWGHWHUPLQHZKLFKHYHQWRFFXUUHGE\H[DPLQLQJWKHHYHQWDUUD\
isc_event[]7KHHYHQWDUUD\LVDXWRPDWLFDOO\FUHDWHGIRUDQDSSOLFDWLRQGXULQJSUHSURFHVVLQJ
(DFKHOHPHQWLQWKHDUUD\FRUUHVSRQGVWRDQHYHQWQDPHSDVVHGDVDQDUJXPHQWWR(9(17
,1,77KHYDOXHRIHDFKHOHPHQWLVWKHQXPEHURIWLPHVWKDWHYHQWRFFXUUHGVLQFHH[HFXWLRQ
RIWKHODVW(9(17:$,7VWDWHPHQWZLWKWKHVDPHUHTXHVWKDQGOH
,QWKHIROORZLQJFRGHDQDSSOLFDWLRQUHJLVWHUVLQWHUHVWLQWKUHHHYHQWVWKHQVXVSHQGV
RSHUDWLRQSHQGLQJHYHQWQRWLILFDWLRQ
EXEC SQL
EVENT INIT RESPOND_MANY ("new_order", "change_order",
"cancel_order");
EXEC SQL
EVENT WAIT RESPOND_MANY;

:KHQDQ\RIWKH´QHZBRUGHUµ´FKDQJHBRUGHUµRU´FDQFHOBRUGHUµHYHQWVDUHSRVWHGDQG
WKHLUFRQWUROOLQJWUDQVDFWLRQVFRPPLWWKHHYHQWPDQDJHUQRWLILHVWKHDSSOLFDWLRQDQG
SURFHVVLQJUHVXPHV7KHIROORZLQJFRGHLOOXVWUDWHVKRZDQDSSOLFDWLRQPLJKWWHVWZKLFKHYHQW
RFFXUUHG

PROGRAMMER’S GUIDE 227


CHAPTER 12 WORKING WITH EVENTS

for (i = 0; i < 3; i++)


{
if (isc_$event[i] > 0)
{
/* this event occurred, so process it */
. . .
}
}

228 INTERBASE 5
CHAPTER

Error Handling and Recovery


Chapter13
13
$OO64/DSSOLFDWLRQVVKRXOGLQFOXGHPHFKDQLVPVIRUWUDSSLQJUHVSRQGLQJWRDQGUHFRYHULQJ
IURPUXQWLPHHUURUVWKHHUURUVWKDWFDQRFFXUZKHQVRPHRQHXVHVDQDSSOLFDWLRQ7KLVFKDSWHU
GHVFULEHVERWKVWDQGDUGSRUWDEOH64/PHWKRGVIRUKDQGOLQJHUURUVDQGDGGLWLRQDOHUURU
KDQGOLQJVSHFLILFWR,QWHU%DVH

Standard error handling


(YHU\WLPHDQ64/VWDWHPHQWLVH[HFXWHGLWUHWXUQVDVWDWXVLQGLFDWRULQWKH64/&2'(
YDULDEOHZKLFKLVGHFODUHGDXWRPDWLFDOO\IRU64/SURJUDPVGXULQJSUHSURFHVVLQJZLWKgpre
7KHIROORZLQJWDEOHVXPPDUL]HVSRVVLEOH64/&2'(YDOXHVDQGWKHLUPHDQLQJV

Value Meaning
0 Success.
1–99 Warning or informational message.
100 End of file (no more data).
<0 Error. Statement failed to complete.
TABLE 13.1 Possible SQLCODE values

229
CHAPTER 13 ERROR HANDLING AND RECOVERY

7RWUDSDQGUHVSRQGWRUXQWLPHHUURUV64/&2'(VKRXOGEHFKHFNHGDIWHUHDFK64/
RSHUDWLRQ7KHUHDUHWKUHHZD\VWRH[DPLQH64/&2'(DQGUHVSRQGWRHUURUV
g 8VH:+(1(9(5VWDWHPHQWVWRDXWRPDWHFKHFNLQJ64/&2'(DQGKDQGOHHUURUVZKHQWKH\
RFFXU
g 7HVW64/&2'(GLUHFWO\DIWHULQGLYLGXDO64/VWDWHPHQWV
g 8VHDMXGLFLRXVFRPELQDWLRQRI:+(1(9(5VWDWHPHQWVDQGGLUHFWWHVWLQJ
(DFKPHWKRGKDVDGYDQWDJHVDQGGLVDGYDQWDJHVGHVFULEHGIXOO\LQWKHUHPDLQGHURIWKLV
FKDSWHU

WHENEVER statements
7KH:+(1(9(5VWDWHPHQWHQDEOHVDOO64/HUURUVWREHKDQGOHGZLWKDPLQLPXPRIFRGLQJ
:+(1(9(5VWDWHPHQWVVSHFLI\HUURUKDQGOLQJFRGHWKDWDSURJUDPVKRXOGH[HFXWHZKHQ
64/&2'(LQGLFDWHVHUURUVZDUQLQJVRUHQGRIILOH7KHV\QWD[RI:+(1(9(5LV
EXEC SQL
WHENEVER {SQLERROR | SQLWARNING | NOT FOUND}
{GOTO label | CONTINUE};

$IWHU:+(1(9(5DSSHDUVLQDSURJUDPDOOVXEVHTXHQW64/VWDWHPHQWVDXWRPDWLFDOO\MXPS
WRWKHVSHFLILHGFRGHORFDWLRQLGHQWLILHGE\ODEHOZKHQWKHDSSURSULDWHHUURURUZDUQLQJ
RFFXUV
%HFDXVHWKH\DIIHFWDOOVXEVHTXHQWVWDWHPHQWV:+(1(9(5VWDWHPHQWVDUHXVXDOO\HPEHGGHG
QHDUWKHVWDUWRIDSURJUDP)RUH[DPSOHWKHILUVWVWDWHPHQWLQWKHIROORZLQJ&FRGH·Vmain()
IXQFWLRQLVD:+(1(9(5WKDWWUDSV64/HUURUV
main()
{
EXEC SQL
WHENEVER SQLERROR GOTO ErrorExit;
. . .
Error Exit:
if (SQLCODE)
{
print_error();
EXEC SQL
ROLLBACK;
EXEC SQL
DISCONNECT;
exit(1);
}

230 INTERBASE 5
STANDARD ERROR HANDLING

}
. . .
print_error()
{
printf("Database error, SQLCODE = %d\n", SQLCODE);
}

8SWRWKUHH:+(1(9(5VWDWHPHQWVFDQEHDFWLYHDWDQ\WLPH
g :+(1(9(564/(5525LVDFWLYDWHGZKHQ64/&2'(LVOHVVWKDQ]HURLQGLFDWLQJWKDWD
VWDWHPHQWIDLOHG
g :+(1(9(564/:$51,1*LVDFWLYDWHGZKHQ64/&2'(FRQWDLQVDYDOXHIURPWR
LQFOXVLYHLQGLFDWLQJWKDWZKLOHDVWDWHPHQWH[HFXWHGWKHUHLVVRPHTXHVWLRQDERXWWKHZD\LW
VXFFHHGHG
g :+(1(9(5127)281'LVDFWLYDWHGZKHQ64/&2'(LVLQGLFDWLQJWKDWHQGRIILOHZDV
UHDFKHGGXULQJD)(7&+RU6(/(&7
2PLWWLQJDVWDWHPHQWIRUDSDUWLFXODUFRQGLWLRQPHDQVLWLVQRWWUDSSHGHYHQLILWRFFXUV)RU
H[DPSOHLI:+(1(9(5127)281'LVOHIWRXWRIDSURJUDPWKHQZKHQD)(7&+RU
6(/(&7HQFRXQWHUVWKHHQGRIILOH64/&2'(LVVHWWREXWSURJUDPH[HFXWLRQFRQWLQXHV
DVLIQRHUURUFRQGLWLRQKDVRFFXUUHG
(UURUFRQGLWLRQVDOVRFDQEHRYHUORRNHGE\XVLQJWKH&217,18(VWDWHPHQWLQVLGHD
:+(1(9(5VWDWHPHQW
. . .
EXEC SQL
WHENEVER SQLWARNING
CONTINUE;
. . .
7KLVFRGHWUDSV64/&2'(ZDUQLQJYDOXHVEXWLJQRUHVWKHP2UGLQDULO\ZDUQLQJVVKRXOGEH
LQYHVWLJDWHGQRWLJQRUHG

,03257$17 8VH:+(1(9(564/(5525&217,18(DWWKHVWDUWRIHUURUKDQGOLQJURXWLQHVWRGLVDEOH
HUURUKDQGOLQJWHPSRUDULO\2WKHUZLVHWKHUHLVDSRVVLELOLW\RIDQLQILQLWHORRSVKRXOG
DQRWKHUHUURURFFXULQWKHKDQGOHULWVHOIWKHURXWLQHZLOOFDOOLWVHOIDJDLQ

SCOPE OF WHENEVER STATEMENTS


:+(1(9(5RQO\DIIHFWVDOOVXEVHTXHQW64/VWDWHPHQWVLQWKHPRGXOHRUVRXUFHFRGHILOH
ZKHUHLWLVGHILQHG,QSURJUDPVZLWKPXOWLSOHVRXUFHFRGHILOHVHDFKPRGXOHPXVWGHILQHLWV
RZQ:+(1(9(5VWDWHPHQWV

PROGRAMMER’S GUIDE 231


CHAPTER 13 ERROR HANDLING AND RECOVERY

CHANGING ERROR-HANDLING ROUTINES


7RVZLWFKWRDQRWKHUHUURUKDQGOLQJURXWLQHIRUDSDUWLFXODUHUURUFRQGLWLRQHPEHGDQRWKHU
:+(1(9(5VWDWHPHQWLQWKHSURJUDPDWWKHSRLQWZKHUHHUURUKDQGOLQJVKRXOGEHFKDQJHG
7KHQHZDVVLJQPHQWRYHUULGHVDQ\SUHYLRXVDVVLJQPHQWDQGUHPDLQVLQHIIHFWXQWLO
RYHUULGGHQLWVHOI)RUH[DPSOHWKHIROORZLQJSURJUDPIUDJPHQWVHWVDQLQLWLDOMXPSSRLQWIRU
64/(5525FRQGLWLRQVWR(UURU([LWWKHQUHVHWVLWWR(UURU([LW
EXEC SQL
WHENEVER SQLERROR
GOTO ErrorExit1;
. . .
EXEC SQL
WHENEVER SQLERROR
GOTO ErrorExit2;
. . .

LIMITATIONS OF WHENEVER STATEMENTS


7KHUHDUHWZROLPLWDWLRQVWR:+(1(9(5,W
g 7UDSVHUURUVLQGLVFULPLQDWHO\)RUH[DPSOH:+(1(9(564/(5525WUDSVERWKPLVVLQJ
GDWDEDVHVDQGGDWDHQWU\WKDWYLRODWHVD&+(&.FRQVWUDLQWDQGMXPSVWRDVLQJOH
HUURUKDQGOLQJURXWLQH:KLOHDPLVVLQJGDWDEDVHLVDVHYHUHHUURUWKDWPD\UHTXLUHDFWLRQ
RXWVLGHWKHFRQWH[WRIWKHFXUUHQWSURJUDPLQYDOLGGDWDHQWU\PD\EHWKHUHVXOWRIDW\SLQJ
PLVWDNHWKDWFRXOGEHIL[HGE\UHHQWHULQJWKHGDWD
g 'RHVQRWHDVLO\HQDEOHDSURJUDPWRUHVXPHSURFHVVLQJDWWKHSRLQWZKHUHWKHHUURURFFXUUHG
)RUH[DPSOHDVLQJOH:+(1(9(564/(5525FDQWUDSGDWDHQWU\WKDWYLRODWHVD&+(&.
FRQVWUDLQWDWVHYHUDOSRLQWVLQDSURJUDPEXWMXPSVWRDVLQJOHHUURUKDQGOLQJURXWLQH,W
PLJKWEHKHOSIXOWRDOORZWKHXVHUWRUHHQWHUGDWDLQWKHVHFDVHVEXWWKHHUURUURXWLQHFDQQRW
GHWHUPLQHZKHUHWRMXPSWRUHVXPHSURJUDPSURFHVVLQJ
(UURUKDQGOLQJURXWLQHVFDQEHYHU\VRSKLVWLFDWHG)RUH[DPSOHLQ&RU&DURXWLQHPLJKW
XVHDODUJHcaseVWDWHPHQWWRH[DPLQH64/&2'(GLUHFWO\DQGUHVSRQGGLIIHUHQWO\WRGLIIHUHQW
YDOXHV(YHQVRFUHDWLQJDVRSKLVWLFDWHGURXWLQHWKDWFDQUHVXPHSURFHVVLQJDWWKHSRLQW
ZKHUHDQHUURURFFXUUHGLVGLIILFXOW7RUHVXPHSURFHVVLQJDIWHUHUURUUHFRYHU\FRQVLGHU
WHVWLQJ64/&2'(GLUHFWO\DIWHUHDFK64/VWDWHPHQWRUFRQVLGHUXVLQJDFRPELQDWLRQRI
HUURUKDQGOLQJPHWKRGV

Testing SQLCODE directly


$SURJUDPFDQWHVW64/&2'(GLUHFWO\DIWHUHDFK64/VWDWHPHQWLQVWHDGRIUHO\LQJRQ
:+(1(9(5WRWUDSDQGKDQGOHDOOHUURUV7KHPDLQDGYDQWDJHWRWHVWLQJ64/&2'(GLUHFWO\
LVWKDWFXVWRPHUURUKDQGOLQJURXWLQHVFDQEHGHVLJQHGIRUSDUWLFXODUVLWXDWLRQV

232 INTERBASE 5
STANDARD ERROR HANDLING

)RUH[DPSOHWKHIROORZLQJ&FRGHIUDJPHQWFKHFNVLI64/&2'(LVQRW]HURDIWHUD6(/(&7
VWDWHPHQWFRPSOHWHV,IVRDQHUURUKDVRFFXUUHGVRWKHVWDWHPHQWVLQVLGHWKHifFODXVHDUH
H[HFXWHG7KHVHVWDWHPHQWVWHVW64/&2'(IRUWZRVSHFLILFYDOXHV
²DQGKDQGOLQJHDFKGLIIHUHQWO\,I64/&2'(LVVHWWRDQ\RWKHUHUURUYDOXHDJHQHULF
HUURUPHVVDJHLVGLVSOD\HGDQGWKHSURJUDPLVHQGHGJUDFHIXOO\
EXEC SQL
SELECT CITY INTO :city FROM STATES
WHERE STATE = :stat:statind;

if (SQLCODE)
{
if (SQLCODE == –1)
printf("too many records found\n");
else if (SQLCODE == 100)
printf("no records found\n");
else
{
printf("Database error, SQLCODE = %d\n", SQLCODE);
EXEC SQL
ROLLBACK;
EXEC SQL
DISCONNECT;
exit(1);
}
}
printf("found city named %s\n", city);
EXEC SQL
COMMIT;
EXEC SQL
DISCONNECT;

7KHGLVDGYDQWDJHWRFKHFNLQJ64/&2'(GLUHFWO\LVWKDWLWUHTXLUHVPDQ\OLQHVRIH[WUDFRGH
MXVWWRVHHLIDQHUURURFFXUUHG2QWKHRWKHUKDQGLWHQDEOHVHUURUVWREHKDQGOHGZLWK
IXQFWLRQFDOOVDVWKHIROORZLQJ&FRGHLOOXVWUDWHV
EXEC SQL
SELECT CITY INTO :city FROM STATES
WHERE STATE = :stat:statind;

switch (SQLCODE)
{
case 0:
break; /* NO ERROR */
case –1

PROGRAMMER’S GUIDE 233


CHAPTER 13 ERROR HANDLING AND RECOVERY

ErrorTooMany();
break;
case 100:
ErrorNotFound();
break;
default:
ErrorExit(); /* Handle all other errors */
break;
}
. . .

8VLQJIXQFWLRQFDOOVIRUHUURUKDQGOLQJHQDEOHVSURJUDPVWRUHVXPHH[HFXWLRQLIHUURUVFDQ
EHFRUUHFWHG

Combining error-handling techniques


(UURUKDQGOLQJLQPDQ\SURJUDPVFDQEHQHILWIURPFRPELQLQJ:+(1(9(5ZLWKGLUHFW
FKHFNLQJRI64/&2'($SURJUDPPLJKWLQFOXGHJHQHULF:+(1(9(5VWDWHPHQWVIRU
KDQGOLQJPRVW64/HUURUFRQGLWLRQVEXWIRUFULWLFDORSHUDWLRQV:+(1(9(5VWDWHPHQWV
PLJKWEHWHPSRUDULO\RYHUULGGHQWRHQDEOHGLUHFWFKHFNLQJRI64/&2'(
)RUH[DPSOHWKHIROORZLQJ&FRGH
g 6HWVXSJHQHULFHUURUKDQGOLQJZLWKWKUHH:+(1(9(5VWDWHPHQWV
g 2YHUULGHVWKH:+(1(9(564/(5525VWDWHPHQWWRIRUFHSURJUDPFRQWLQXDWLRQXVLQJWKH
&217,18(FODXVH
g &KHFNV64/&2'(GLUHFWO\
g 2YHUULGHV:+(1(9(564/(5525DJDLQWRUHVHWLW
main()
{
EXEC SQL
WHENEVER SQLERROR GOTO ErrorExit; /* trap all errors */
EXEC SQL
WHENEVER SQLWARNING GOTO WarningExit; /* trap warnings */
EXEC SQL
WHENEVER NOT FOUND GOTO AllDone; /* trap end of file */
. . .
EXEC SQL
WHENEVER SQLERROR CONTINUE; /* prevent trapping of errors */
EXEC SQL
SELECT CITY INTO :city FROM STATES
WHERE STATE = :stat:statind;

234 INTERBASE 5
STANDARD ERROR HANDLING

switch (SQLCODE)
{
case 0:
break; /* NO ERROR */
case –1
ErrorTooMany();
break;
case 100:
ErrorNotFound();
break;
default:
ErrorExitFunction(); /* Handle all other errors */
break;
}
EXEC SQL
WHENEVER SQLERROR GOTO ErrorExit; /* reset to trap all errors */
. . .
}

Guidelines for error handling


7KHIROORZLQJJXLGHOLQHVDSSO\WRDOOHUURUKDQGOLQJURXWLQHVLQDSURJUDP

USING SQL AND HOST-LANGUAGE STATEMENTS


$OO64/VWDWHPHQWVDQG,QWHU%DVHIXQFWLRQVFDQEHXVHGLQHUURUKDQGOLQJURXWLQHVH[FHSW
IRU&211(&7
$Q\KRVWODQJXDJHVWDWHPHQWVDQGIXQFWLRQVFDQDSSHDULQDQHUURUKDQGOLQJURXWLQHZLWKRXW
UHVWULFWLRQ

,03257$17 8VH:+(1(9(564/(5525&217,18(DWWKHVWDUWRIHUURUKDQGOLQJURXWLQHVWRGLVDEOH
HUURUKDQGOLQJWHPSRUDULO\2WKHUZLVHWKHUHLVDSRVVLELOLW\RIDQLQILQLWHORRSVKRXOG
DQRWKHUHUURURFFXULQWKHKDQGOHULWVHOIWKHURXWLQHZLOOFDOOLWVHOIDJDLQ

NESTING ERROR-HANDLING ROUTINES


$OWKRXJKHUURUKDQGOLQJURXWLQHVFDQEHQHVWHGRUFDOOHGUHFXUVLYHO\WKLVSUDFWLFHLVQRW
UHFRPPHQGHGXQOHVVWKHSURJUDPSUHVHUYHVWKHRULJLQDOFRQWHQWVRI64/&2'(DQGWKH
,QWHU%DVHHUURUVWDWXVDUUD\

PROGRAMMER’S GUIDE 235


CHAPTER 13 ERROR HANDLING AND RECOVERY

HANDLING UNEXPECTED AND UNRECOVERABLE ERRORS


(YHQLIDQHUURUKDQGOLQJURXWLQHFDWFKHVDQGKDQGOHVUHFRYHUDEOHHUURUVLWVKRXOGDOZD\V
FRQWDLQVWDWHPHQWVWRKDQGOHXQH[SHFWHGRUXQUHFRYHUDEOHHUURUV
7KHIROORZLQJFRGHKDQGOHVXQUHFRYHUDEOHHUURUV
. . .
isc_print_sqlerr(SQLCODE, isc_status);
EXEC SQL
ROLLBACK;
EXEC SQL
DISCONNECT;
exit(1);

PORTABILITY
)RUSRUWDELOLW\DPRQJGLIIHUHQW64/LPSOHPHQWDWLRQV64/SURJUDPVVKRXOGOLPLWHUURU
KDQGOLQJWR:+(1(9(5VWDWHPHQWVRUGLUHFWH[DPLQDWLRQRI64/&2'(YDOXHV
,QWHU%DVHLQWHUQDOHUURUUHFRJQLWLRQRFFXUVDWDILQHUOHYHORIJUDQXODULW\WKDQ64/&2'(
UHSUHVHQWDWLRQSHUPLWV$VLQJOH64/&2'(YDOXHFDQUHSUHVHQWPDQ\GLIIHUHQWLQWHUQDO
,QWHU%DVHHUURUV:KHUHSRUWDELOLW\LVQRWDQLVVXHLWPD\EHGHVLUDEOHWRSHUIRUPDGGLWLRQDO
,QWHU%DVHHUURUKDQGOLQJ7KHUHPDLQGHURIWKLVFKDSWHUH[SODLQVKRZWRXVHWKHVHDGGLWLRQDO
IHDWXUHV

Additional InterBase error handling


7KHVDPH64/&2'(YDOXHFDQEHUHWXUQHGE\PXOWLSOH,QWHU%DVHHUURUV)RUH[DPSOHWKH
64/&2'(YDOXH²LVJHQHUDWHGLQUHVSRQVHWRPDQ\GLIIHUHQW,QWHU%DVHHUURUV:KHQ
SRUWDELOLW\WRRWKHUYHQGRUV·64/LPSOHPHQWDWLRQVLVQRWUHTXLUHG64/SURJUDPVFDQ
VRPHWLPHVH[DPLQHWKH,QWHU%DVHHUURUVWDWXVDUUD\LVFBVWDWXVIRUPRUHVSHFLILFHUURU
LQIRUPDWLRQ
LVFBVWDWXVLVDQDUUD\RIWZHQW\HOHPHQWVRIW\SH,6&B67$786,WLVGHFODUHGDXWRPDWLFDOO\IRU
SURJUDPVZKHQWKH\DUHSUHSURFHVVHGZLWKgpre7ZRNLQGVRI,QWHU%DVHHUURULQIRUPDWLRQ
DUHUHSRUWHGLQWKHVWDWXVDUUD\
g ,QWHU%DVHHUURUPHVVDJHFRPSRQHQWV
g ,QWHU%DVHHUURUQXPEHUV
$VORQJDVWKHFXUUHQW64/&2'(YDOXHLVQRW²RUHUURUKDQGOLQJURXWLQHVWKDW
H[DPLQHWKHHUURUVWDWXVDUUD\FDQGRDQ\RIWKHIROORZLQJ
g 'LVSOD\64/DQG,QWHU%DVHHUURUPHVVDJHV

236 INTERBASE 5
ADDITIONAL INTERBASE ERROR HANDLING

g &DSWXUH64/DQG,QWHU%DVHHUURUPHVVDJHVWRDVWRUDJHEXIIHUIRUIXUWKHUPDQLSXODWLRQ
g 7UDSIRUDQGUHVSRQGWRSDUWLFXODU,QWHU%DVHHUURUFRGHV
7KH,QWHU%DVHHUURUVWDWXVDUUD\LVXVXDOO\H[DPLQHGRQO\DIWHUWUDSSLQJHUURUVZLWK
:+(1(9(5RUWHVWLQJ64/&2'(GLUHFWO\

Displaying error messages


,I64/&2'(LVOHVVWKDQ²DGGLWLRQDO,QWHU%DVHHUURULQIRUPDWLRQFDQEHGLVSOD\HGXVLQJ
WKH,QWHU%DVHisc_print_sqlerror()IXQFWLRQLQVLGHDQHUURUKDQGOLQJURXWLQH'XULQJ
SUHSURFHVVLQJZLWKgpreWKLVIXQFWLRQLVDXWRPDWLFDOO\GHFODUHGIRU,QWHU%DVHDSSOLFDWLRQV
isc_print_sqlerror()GLVSOD\VWKH64/&2'(YDOXHDUHODWHG64/HUURUPHVVDJHDQGDQ\
,QWHU%DVHHUURUPHVVDJHVLQWKHVWDWXVDUUD\,WUHTXLUHVWZRSDUDPHWHUV64/&2'(DQGD
SRLQWHUWRWKHHUURUVWDWXVDUUD\isc_status
)RUH[DPSOHZKHQDQHUURURFFXUVWKHIROORZLQJFRGHGLVSOD\VWKHYDOXHRI64/&2'(
GLVSOD\VDFRUUHVSRQGLQJ64/HUURUPHVVDJHWKHQGLVSOD\VDGGLWLRQDO,QWHU%DVHHUURU
PHVVDJHLQIRUPDWLRQLISRVVLEOH
. . .
EXEC SQL
SELECT CITY INTO :city FROM STATES
WHERE STATE = :stat:statind;
if(SQLCODE)
{
isc_print_sqlerror(SQLCODE, isc_status);
EXEC SQL
ROLLBACK;
EXEC SQL
DISCONNECT ALL;
exit(1);
}
. . .

,03257$17 6RPHZLQGRZLQJV\VWHPVGRQRWHQFRXUDJHRUSHUPLWGLUHFWVFUHHQZULWHV'RQRWXVH
isc_print_sqlerror()ZKHQGHYHORSLQJDSSOLFDWLRQVIRUWKHVHHQYLURQPHQWV,QVWHDGXVH
isc_sql_interprete()DQGisc_interprete()WRFDSWXUHPHVVDJHVWRDEXIIHUIRUGLVSOD\

PROGRAMMER’S GUIDE 237


CHAPTER 13 ERROR HANDLING AND RECOVERY

Capturing SQL error messages


,QVWHDGRIGLVSOD\LQJ64/HUURUPHVVDJHVDQDSSOLFDWLRQFDQFDSWXUHWKHWH[WRIWKRVH
PHVVDJHVLQDEXIIHUE\XVLQJisc_sql_interprete()&DSWXUHPHVVDJHVLQDEXIIHUZKHQ
DSSOLFDWLRQV
g 5XQXQGHUZLQGRZLQJV\VWHPVWKDWGRQRWSHUPLWGLUHFWZULWLQJWRWKHVFUHHQ
g 6WRUHDUHFRUGRIDOOHUURUPHVVDJHVLQDORJILOH
g 0DQLSXODWHRUIRUPDWHUURUPHVVDJHVIRUGLVSOD\
*LYHQ64/&2'(DSRLQWHUWRDVWRUDJHEXIIHUDQGWKHPD[LPXPVL]HRIWKHEXIIHULQE\WHV
isc_sql_interprete()EXLOGVDQ64/HUURUPHVVDJHVWULQJDQGSXWVWKHIRUPDWWHGVWULQJLQ
WKHEXIIHUZKHUHLWFDQEHPDQLSXODWHG$EXIIHUVL]HRIE\WHVLVODUJHHQRXJKWRKROGDQ\
64/HUURUPHVVDJH
)RUH[DPSOHWKHIROORZLQJFRGHVWRUHVDQ64/HUURUPHVVDJHLQHUUBEXIWKHQZULWHVHUUBEXI
WRDORJILOH
. . .
char err_buf[256]; /* error message buffer for isc_sql_interprete() */
FILE *efile=NULL; /* code fragment assumes pointer to an open file */
. . .
EXEC SQL
SELECT CITY INTO :city FROM STATES
WHERE STATE = :stat:statind;
if (SQLCODE)
{
isc_sql_interprete(SQLCODE, err_buf, sizeof(err_buf));
if(efile==NULL) efile=fopen("errors", "w");
fprintf(efile, "%s\n", err_buf); /* write buffer to log file */
EXEC SQL
ROLLBACK; /* undo database changes */
EXEC SQL
DISCONNECT ALL; /* close open databases */
exit(1); /* exit with error flag set */
}
. . .

isc_sql_interprete()UHWULHYHVDQGIRUPDWVDVLQJOHPHVVDJHFRUUHVSRQGLQJWRDJLYHQ
64/&2'(:KHQ64/&2'(LVOHVVWKDQ²PRUHVSHFLILF,QWHU%DVHHUURULQIRUPDWLRQLV
DYDLODEOH,WWRRFDQEHUHWULHYHGIRUPDWWHGDQGVWRUHGLQDEXIIHUE\XVLQJWKH
isc_interprete()IXQFWLRQ

238 INTERBASE 5
ADDITIONAL INTERBASE ERROR HANDLING

Capturing InterBase error messages


7KHWH[WRI,QWHU%DVHHUURUPHVVDJHVFDQEHFDSWXUHGLQDEXIIHUE\XVLQJisc_interprete()
&DSWXUHPHVVDJHVLQDEXIIHUZKHQDSSOLFDWLRQV
g 5XQXQGHUZLQGRZLQJV\VWHPVWKDWGRQRWSHUPLWGLUHFWZULWLQJWRWKHVFUHHQ
g 6WRUHDUHFRUGRIDOOHUURUPHVVDJHVLQDORJILOH
g 0DQLSXODWHRUIRUPDWHUURUPHVVDJHVIRUGLVSOD\

,03257$17 isc_interprete()VKRXOGQRWEHXVHGXQOHVV64/&2'(LVOHVVWKDQ²EHFDXVHWKHFRQWHQWV
RIisc_statusPD\QRWFRQWDLQUHOLDEOHHUURULQIRUPDWLRQLQWKHVHFDVHV
*LYHQERWKWKHORFDWLRQRIDVWRUDJHEXIIHUSUHYLRXVO\DOORFDWHGE\WKHSURJUDPDQGDSRLQWHU
WRWKHVWDUWRIWKHVWDWXVDUUD\isc_interprete()EXLOGVDQHUURUPHVVDJHVWULQJIURPWKH
LQIRUPDWLRQLQWKHVWDWXVDUUD\DQGSXWVWKHIRUPDWWHGVWULQJLQWKHEXIIHUZKHUHLWFDQEH
PDQLSXODWHG,WDOVRDGYDQFHVWKHVWDWXVDUUD\SRLQWHUWRWKHVWDUWRIWKHQH[WFOXVWHURI
DYDLODEOHHUURULQIRUPDWLRQ
isc_interprete()UHWULHYHVDQGIRUPDWVDVLQJOHHUURUPHVVDJHHDFKWLPHLWLVFDOOHG:KHQDQ
HUURURFFXUVLQDQ,QWHU%DVHSURJUDPKRZHYHUWKHVWDWXVDUUD\PD\FRQWDLQPRUHWKDQRQH
HUURUPHVVDJH7RUHWULHYHDOOUHOHYDQWHUURUPHVVDJHVHUURUKDQGOLQJURXWLQHVVKRXOG
UHSHDWHGO\FDOOisc_interprete()XQWLOLWUHWXUQVQRPRUHPHVVDJHV
%HFDXVHisc_interprete()PRGLILHVWKHSRLQWHUWRWKHVWDWXVDUUD\WKDWLWUHFHLYHVGRQRWSDVV
LVFBVWDWXVGLUHFWO\WRLW,QVWHDGGHFODUHDSRLQWHUWRisc_statusWKHQSDVVWKHSRLQWHUWR
isc_interprete()
7KHIROORZLQJ&FRGHIUDJPHQWLOOXVWUDWHVKRZ,QWHU%DVHHUURUPHVVDJHVFDQEHFDSWXUHGWR
DORJILOHDQGGHPRQVWUDWHVWKHSURSHUGHFODUDWLRQRIDVWULQJEXIIHUDQGSRLQWHUWRLVFBVWDWXV
,WDVVXPHVWKHORJILOHLVSURSHUO\GHFODUHGDQGRSHQHGEHIRUHFRQWUROLVSDVVHGWRWKH
HUURUKDQGOLQJURXWLQH,WDOVRGHPRQVWUDWHVKRZWRVHWWKHSRLQWHUWRWKHVWDUWRIWKHVWDWXV
DUUD\LQWKHHUURUKDQGOLQJURXWLQHEHIRUHisc_interprete()LVILUVWFDOOHG
. . .
#include "ibase.h";
. . .
main()
{
char msg[512];
ISC_STATUS *vector;
FILE *efile; /* code fragment assumes pointer to an open file */
. . .
if (SQLCODE < –1)
ErrorExit();
}

PROGRAMMER’S GUIDE 239


CHAPTER 13 ERROR HANDLING AND RECOVERY

. . .

ErrorExit()
{
vector = isc_status; /* (re)set to start of status vector */
isc_interprete(msg, &vector); /* retrieve first mesage */
fprintf(efile, "%s\n", msg); /* write buffer to log file */
msg[0] = ’-’; /* append leading hyphen to secondary messages */
while (isc_interprete(msg + 1, &vector)) /* more?*/
fprintf(efile, "%s\n", msg); /* if so, write it to log */
fclose(efile); /* close log prior to quitting program */
EXEC SQL
ROLLBACK;
EXEC SQL
DISCONNECT ALL;
exit(1); /* quit program with an ’abnormal termination’ code */
}
. . .

,QWKLVH[DPSOHWKHHUURUKDQGOLQJURXWLQHSHUIRUPVWKHIROORZLQJWDVNV
g 6HWVWKHHUURUDUUD\SRLQWHUWRWKHVWDUWLQJDGGUHVVRIWKHVWDWXVYHFWRUisc_status
g &DOOV isc_interprete()DVLQJOHWLPHWRUHWULHYHWKHILUVWHUURUPHVVDJHIURPWKHVWDWXVYHFWRU
g :ULWHVWKHILUVWPHVVDJHWRDORJILOH
g 0DNHVUHSHDWHGFDOOVWRisc_interprete()ZLWKLQD:+,/(ORRSWRUHWULHYHDQ\DGGLWLRQDO
PHVVDJHV,IDGGLWLRQDOPHVVDJHVDUHUHWULHYHGWKH\DUHDOVRZULWWHQWRWKHORJILOH
g 5ROOVEDFNWKHWUDQVDFWLRQ
g &ORVHVWKHGDWDEDVHDQGUHOHDVHVV\VWHPUHVRXUFHV

Handling InterBase error codes


:KHQHYHU64/&2'(LVOHVVWKDQ²WKHHUURUVWDWXVDUUD\LVFBVWDWXVPD\FRQWDLQGHWDLOHG
HUURULQIRUPDWLRQVSHFLILFWR,QWHU%DVHLQFOXGLQJHUURUFRGHVQXPEHUVWKDWXQLTXHO\LGHQWLI\
HDFKHUURU:LWKFDUHHUURUKDQGOLQJURXWLQHVFDQWUDSIRUDQGUHVSRQGWRVSHFLILFFRGHV
7RWUDSDQGKDQGOH,QWHU%DVHHUURUFRGHVLQDQHUURUKDQGOLQJURXWLQHIROORZWKHVHVWHSV
 &KHFN64/&2'(WREHVXUHLWLVOHVVWKDQ²
 &KHFNWKDWWKHILUVWHOHPHQWRIWKHVWDWXVDUUD\LVVHWWRLVFBDUJBJGVLQGLFDWLQJWKDW
DQ,QWHU%DVHHUURUFRGHLVDYDLODEOH,Q&SURJUDPVWKHILUVWHOHPHQWRIWKHVWDWXV
DUUD\LVLVFBVWDWXV>@

240 INTERBASE 5
ADDITIONAL INTERBASE ERROR HANDLING

'RQRWDWWHPSWWRKDQGOHHUURUVUHSRUWHGLQWKHVWDWXVDUUD\LIWKHILUVWVWDWXVDUUD\HOHPHQW
FRQWDLQVDYDOXHRWKHUWKDQ
 ,I64/&2'(LVOHVVWKDQ²DQGWKHILUVWHOHPHQWLQLVFBVWDWXVLVVHWWRLVFBDUJBJGV
XVHWKHDFWXDO,QWHU%DVHHUURUFRGHLQWKHVHFRQGHOHPHQWRILVFBVWDWXVWREUDQFK
WRDQDSSURSULDWHURXWLQHIRUWKDWHUURU

7,3 ,QWHU%DVHHUURUFRGHVDUHPDSSHGWRPQHPRQLFGHILQLWLRQV IRUH[DPSOHisc_arg_gds WKDW


FDQEHXVHGLQFRGHWRPDNHLWHDVLHUWRUHDGXQGHUVWDQGDQGPDLQWDLQ'HILQLWLRQVIRUDOO
,QWHU%DVHHUURUFRGHVFDQEHIRXQGLQWKHLEDVHKILOH
7KHIROORZLQJ&FRGHIUDJPHQWLOOXVWUDWHVDQHUURUKDQGOLQJURXWLQHWKDW
g 'LVSOD\VHUURUPHVVDJHVZLWKisc_print_sqlerror()
g ,OOXVWUDWHVKRZWRSDUVHIRUDQGKDQGOHVL[VSHFLILF,QWHU%DVHHUURUVZKLFKPLJKWEHFRUUHFWHG
XSRQUROOEDFNGDWDHQWU\DQGUHWU\
g 8VHVPQHPRQLFGHILQLWLRQVIRU,QWHU%DVHHUURUQXPEHUV
. . .
int c, jval, retry_flag = 0;
jmp_buf jumper;
. . .
main()
{
. . .
jval = setjmp(jumper);
if (retry_flag)
ROLLBACK;
. . .
}
int ErrorHandler(void)
{
retry_flag = 0; /* reset to 0, no retry */
isc_print_sqlerror(SQLCODE, isc_status); /* display errors */
if (SQLCODE < –1)
{
if (isc_status[0] == isc_arg_gds)
{
switch (isc_status[1])
{
case isc_convert_error:
case isc_deadlock:
case isc_integ_fail:
case isc_lock_conflict:
case isc_no_dup:

PROGRAMMER’S GUIDE 241


CHAPTER 13 ERROR HANDLING AND RECOVERY

case isc_not_valid:
printf("\n Do you want to try again? (Y/N)");
c = getchar();
if (c == ’Y’ || c == ’y’)
{
retry_flag = 1; /* set flag to retry */
longjmp(jumper, 1);
}
break;
case isc_end_arg: /* there really isn’t an error */
retry_flag = 1; /* set flag to retry */
longjump(jumper, 1);
break;
default: /* we can’t handle everything, so abort */
break;
}
}
}
EXEC SQL
ROLLBACK;
EXEC SQL
DISCONNECT ALL;
exit(1);
}

242 INTERBASE 5
CHAPTER

Using Dynamic SQL


Chapter14
14
7KLVFKDSWHUGHVFULEHVKRZWRZULWHG\QDPLF64/DSSOLFDWLRQVDSSOLFDWLRQVWKDWHOLFLWRU
EXLOG64/VWDWHPHQWVIRUH[HFXWLRQDWUXQWLPH
,QPDQ\GDWDEDVHDSSOLFDWLRQVWKHSURJUDPPHUVSHFLILHVH[DFWO\ZKLFK64/VWDWHPHQWVWR
H[HFXWHDJDLQVWDSDUWLFXODUGDWDEDVH:KHQWKHDSSOLFDWLRQLVFRPSLOHGWKHVHVWDWHPHQWV
EHFRPHIL[HG,QVRPHGDWDEDVHDSSOLFDWLRQVLWLVXVHIXOWREXLOGDQGH[HFXWHVWDWHPHQWVIURP
WH[WVWULQJIUDJPHQWVRUIURPVWULQJVHOLFLWHGIURPWKHXVHUDWUXQWLPH7KHVHDSSOLFDWLRQV
UHTXLUHWKHFDSDELOLW\WRFUHDWHDQGH[HFXWH64/VWDWHPHQWVG\QDPLFDOO\DWUXQWLPH'\QDPLF
64/ '64/ SURYLGHVWKLVFDSDELOLW\)RUH[DPSOHWKH,QWHU%DVHisql XWLOLW\LVD'64/
DSSOLFDWLRQ

Overview of the DSQL programming process


%XLOGLQJDQGH[HFXWLQJ'64/VWDWHPHQWVLQYROYHVWKHIROORZLQJJHQHUDOVWHSV
g (PEHGGLQJ64/VWDWHPHQWVWKDWVXSSRUW'64/SURFHVVLQJLQDQDSSOLFDWLRQ
g 8VLQJKRVWODQJXDJHIDFLOLWLHVVXFKDVGDWDW\SHVDQGPDFURVWRSURYLGHLQSXWDQGRXWSXW
DUHDVIRUSDVVLQJVWDWHPHQWVDQGSDUDPHWHUVDWUXQWLPH
g 3URJUDPPLQJPHWKRGVWKDWXVHWKHVHVWDWHPHQWVDQGIDFLOLWLHVWRSURFHVV64/VWDWHPHQWVDW
UXQWLPH
7KHVHVWHSVDUHGHVFULEHGLQGHWDLOWKURXJKRXWWKLVFKDSWHU

243
CHAPTER 14 USING DYNAMIC SQL

DSQL limitations
$OWKRXJK'64/RIIHUVPDQ\DGYDQWDJHVLWDOVRKDVWKHIROORZLQJOLPLWDWLRQV
g $FFHVVWRRQHGDWDEDVHDWDWLPH
g '\QDPLFWUDQVDFWLRQSURFHVVLQJLVQRWSHUPLWWHGDOOQDPHGWUDQVDFWLRQVPXVWEHGHFODUHGDW
FRPSLOHWLPH
g '\QDPLFDFFHVVWR%OREDQGDUUD\GDWDLVQRWVXSSRUWHG%OREDQGDUUD\GDWDFDQEHDFFHVVHG
EXWRQO\WKURXJKVWDQGDUGVWDWLFDOO\SURFHVVHG64/VWDWHPHQWVRUWKURXJKORZOHYHO$3,
FDOOV
g 'DWDEDVHFUHDWLRQLVUHVWULFWHGWR&5($7('$7$%$6(VWDWHPHQWVH[HFXWHGZLWKLQWKHFRQWH[W
RI(;(&87(,00(',$7(
)RUPRUHLQIRUPDWLRQDERXWGDWDEDVHDFFHVVLQ'64/VHH´$FFHVVLQJGDWDEDVHVµRQ
SDJH )RUPRUHLQIRUPDWLRQDERXWKDQGOLQJWUDQVDFWLRQVLQ'64/DSSOLFDWLRQVVHH
´+DQGOLQJWUDQVDFWLRQVµRQSDJH )RUPRUHLQIRUPDWLRQDERXWZRUNLQJZLWK%OREGDWD
LQ'64/VHH´3URFHVVLQJ%OREGDWDµRQSDJH )RUPRUHLQIRUPDWLRQDERXWKDQGOLQJ
DUUD\GDWDLQ'64/VHH´3URFHVVLQJDUUD\GDWDµRQSDJH )RUPRUHLQIRUPDWLRQDERXW
G\QDPLFFUHDWLRQRIGDWDEDVHVVHH´&UHDWLQJDGDWDEDVHµRQSDJH 

Accessing databases
8VLQJVWDQGDUG64/V\QWD[D'64/DSSOLFDWLRQFDQRQO\XVHRQHGDWDEDVHKDQGOHSHUVRXUFH
ILOHPRGXOHDQGFDQWKHUHIRUHRQO\EHFRQQHFWHGWRDVLQJOHGDWDEDVHDWDWLPH'DWDEDVH
KDQGOHVPXVWEHGHFODUHGDQGLQLWLDOL]HGZKHQDQDSSOLFDWLRQLVSUHSURFHVVHGZLWKgpre)RU
H[DPSOHWKHIROORZLQJFRGHFUHDWHVDVLQJOHKDQGOHGEDQGLQLWLDOL]HVLWWR]HUR
#include "ibase.h"
isc_db_handle db1;
. . .
db1 = 0L;

$IWHUDGDWDEDVHKDQGOHLVGHFODUHGDQGLQLWLDOL]HGLWFDQEHDVVLJQHGG\QDPLFDOO\WRDGDWDEDVH
DWUXQWLPHDVIROORZV
char dbname[129];
. . .
prompt_user("Name of database to open: ");
gets(dbname);
EXEC SQL
SET DATABASE db1 = :dbname;
EXEC SQL

244 INTERBASE 5
DSQL LIMITATIONS

CONNECT db1;
. . .

7KHGDWDEDVHDFFHVVHGE\'64/VWDWHPHQWVLVDOZD\VWKHODVWGDWDEDVHKDQGOHPHQWLRQHGLQ
D6(7'$7$%$6(FRPPDQG$GDWDEDVHKDQGOHFDQEHXVHGWRFRQQHFWWRGLIIHUHQWGDWDEDVHV
DVORQJDVDSUHYLRXVO\FRQQHFWHGGDWDEDVHLVILUVWGLVFRQQHFWHGZLWK',6&211(&7
',6&211(&7DXWRPDWLFDOO\VHWVGDWDEDVHKDQGOHVWR18//7KHIROORZLQJVWDWHPHQWV
GLVFRQQHFWIURPDGDWDEDVH]HURWKHGDWDEDVHKDQGOHDQGFRQQHFWWRDQHZGDWDEDVH
EXEC SQL
DISCONNECT db1;
EXEC SQL
SET DATABASE db1 = "employee.gdb";
EXEC SQL
CONNECT db1;

7RDFFHVVPRUHWKDQRQHGDWDEDVHXVLQJ'64/FUHDWHDVHSDUDWHVRXUFHILOHPRGXOHIRUHDFK
GDWDEDVHDQGXVHORZOHYHO$3,FDOOVWRDWWDFKWRWKHGDWDEDVHVDQGDFFHVVGDWD)RUPRUH
LQIRUPDWLRQDERXWDFFHVVLQJGDWDEDVHVZLWK$3,FDOOVVHHWKH$3,*XLGH)RUPRUH
LQIRUPDWLRQDERXW64/GDWDEDVHVWDWHPHQWVVHH&KDSWHU´:RUNLQJZLWK'DWDEDVHVµ

Handling transactions
,QWHU%DVHUHTXLUHVWKDWDOOWUDQVDFWLRQQDPHVEHGHFODUHGZKHQDQDSSOLFDWLRQLVSUHSURFHVVHG
ZLWKgpre2QFHIL[HGDWSUHFRPSLOHWLPHWUDQVDFWLRQKDQGOHVFDQQRWEHFKDQJHGDWUXQWLPH
QRUFDQQHZKDQGOHVEHGHFODUHGG\QDPLFDOO\DWUXQWLPH
64/VWDWHPHQWVVXFKDV35(3$5('(6&5,%((;(&87(DQG(;(&87(,00(',$7(FDQ
EHFRGHGDWSUHFRPSLOHWLPHWRLQFOXGHDQRSWLRQDO75$16$&7,21FODXVHVSHFLI\LQJZKLFK
WUDQVDFWLRQFRQWUROVVWDWHPHQWH[HFXWLRQ7KHIROORZLQJFRGHGHFODUHVLQLWLDOL]HVDQGXVHVD
WUDQVDFWLRQKDQGOHLQDVWDWHPHQWWKDWSURFHVVHVDUXQWLPH'64/VWDWHPHQW
#include "ibase.h"
isc_tr_handle t1;
. . .
t1 = 0L;
EXEC SQL
SET TRANSACTION NAME t1;
EXEC SQL
PREPARE TRANSACTION t1 Q FROM :sql_buf;

'64/VWDWHPHQWVWKDWDUHSURFHVVHGZLWK35(3$5('(6&5,%((;(&87(DQG(;(&87(
,00(',$7(FDQQRWXVHD75$16$&7,21FODXVHHYHQLILWLVSHUPLWWHGLQVWDQGDUG
HPEHGGHG64/

PROGRAMMER’S GUIDE 245


CHAPTER 14 USING DYNAMIC SQL

7KH6(775$16$&7,21VWDWHPHQWFDQQRWEHSUHSDUHGEXWLWFDQEHSURFHVVHGZLWK
(;(&87(,00(',$7(LI
 3UHYLRXVWUDQVDFWLRQVDUHILUVWFRPPLWWHGRUUROOHGEDFN
 7KHWUDQVDFWLRQKDQGOHLVVHWWR18//
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVFRPPLWWKHSUHYLRXVGHIDXOWWUDQVDFWLRQWKHQVWDUWD
QHZRQHZLWK(;(&87(,00(',$7( 
EXEC SQL
COMMIT;
/* set default transaction name to NULL */
gds__trans = NULL;
EXEC SQL
EXECUTE IMMEDIATE "SET TRANSACTION READ ONLY";

Creating a database
7RFUHDWHDQHZGDWDEDVHLQD'64/DSSOLFDWLRQ
 'LVFRQQHFWIURPDQ\FXUUHQWO\DWWDFKHGGDWDEDVHV'LVFRQQHFWLQJIURPD
GDWDEDVHDXWRPDWLFDOO\VHWVLWVGDWDEDVHKDQGOHWR18//
 %XLOGWKH&5($7('$7$%$6(VWDWHPHQWWRSURFHVV
 ([HFXWHWKHVWDWHPHQWZLWK(;(&87(,00(',$7(
)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVGLVFRQQHFWIURPDQ\FXUUHQWO\FRQQHFWHGGDWDEDVHV
DQGFUHDWHDQHZGDWDEDVH$Q\H[LVWLQJGDWDEDVHKDQGOHVDUHVHWWR18//VRWKDWWKH\FDQEH
XVHGWRFRQQHFWWRWKHQHZGDWDEDVHLQIXWXUH'64/VWDWHPHQWV
char *str = "CREATE DATABASE \"new_emp.gdb\"";
. . .
EXEC SQL
DISCONNECT ALL;
EXEC SQL
EXECUTE IMMEDIATE :str;

Processing Blob data


'64/GRHVQRWGLUHFWO\VXSSRUW%ORESURFHVVLQJ%OREFXUVRUVDUHQRWVXSSRUWHGLQ'64/
'64/DSSOLFDWLRQVFDQXVH$3,FDOOVWRSURFHVV%OREGDWD)RUPRUHLQIRUPDWLRQDERXW%ORE
$3,FDOOVVHHWKH$3,*XLGH

246 INTERBASE 5
WRITING A DSQL APPLICATION

Processing array data


'64/GRHVQRWGLUHFWO\VXSSRUWDUUD\SURFHVVLQJ'64/DSSOLFDWLRQVFDQXVH$3,FDOOVWR
SURFHVVDUUD\GDWD)RUPRUHLQIRUPDWLRQDERXWDUUD\$3,FDOOVVHHWKH$3,*XLGH

Writing a DSQL application


:ULWHD'64/DSSOLFDWLRQZKHQDQ\RIWKHIROORZLQJDUHQRWNQRZQXQWLOUXQWLPH
g 7KHWH[WRIWKH64/VWDWHPHQW
g 7KHQXPEHURIKRVWYDULDEOHV
g 7KHGDWDW\SHVRIKRVWYDULDEOHV
g 5HIHUHQFHVWRGDWDEDVHREMHFWV
:ULWLQJD'64/DSSOLFDWLRQLVXVXDOO\PRUHFRPSOH[WKDQSURJUDPPLQJZLWKUHJXODU64/
EHFDXVHIRUPRVW'64/RSHUDWLRQVWKHDSSOLFDWLRQQHHGVH[SOLFLWO\WRDOORFDWHDQGSURFHVV
DQH[WHQGHG64/GHVFULSWRUDUHD ;64/'$ GDWDVWUXFWXUHWRSDVVGDWDWRDQGIURPWKH
GDWDEDVH
7RXVH'64/WRSURFHVVDQ64/VWDWHPHQWIROORZWKHVHEDVLFVWHSV
 'HWHUPLQHLI'64/FDQSURFHVVWKH64/VWDWHPHQW
 5HSUHVHQWWKH64/VWDWHPHQWDVDFKDUDFWHUVWULQJLQWKHDSSOLFDWLRQ
 ,IQHFHVVDU\DOORFDWHRQHRUPRUH;64/'$VIRULQSXWSDUDPHWHUVDQGUHWXUQ
YDOXHV
 8VHDQDSSURSULDWH'64/SURJUDPPLQJPHWKRGWRSURFHVVWKH64/VWDWHPHQW

PROGRAMMER’S GUIDE 247


CHAPTER 14 USING DYNAMIC SQL

SQL statements DSQL can process


'64/FDQSURFHVVPRVWEXWQRWDOO64/VWDWHPHQWV7KHIROORZLQJWDEOHOLVWV64/VWDWHPHQW
WKDWDUHDYDLODEOHWR'64/

ALTER DATABASE CREATE ROLE DROP ROLE


ALTER DOMAIN CREATE SHADOW DROP SHADOW
ALTER EXCEPTION CREATE TABLE DROP TABLE
ALTER INDEX CREATE TRIGGER DROP TRIGGER
ALTER PROCEDURE CREATE VIEW DROP VIEW
ALTER TABLE DECLARE EXTERNAL FUNCTION EXECUTE PROCEDURE
ALTER TRIGGER DECLARE FILTER GRANT
COMMIT DELETE INSERT
CONNECT DROP DATABASE INSERT CURSOR (BLOB)
CREATE DATABASE DROP DOMAIN REVOKE
CREATE DOMAIN DROP EXCEPTION ROLLBACK
CREATE EXCEPTION DROP EXTERNAL FUNCTION SELECT
CREATE GENERATOR DROP FILTER SET GENERATOR
CREATE INDEX DROP INDEX UPDATE
CREATE PROCEDURE DROP PROCEDURE

7KHIROORZLQJ(64/VWDWHPHQWVFDQQRWEHSURFHVVHGE\'64/&/26('(&/$5(&85625
'(6&5,%((;(&87((;(&87(,00(',$7()(7&+23(135(3$5(
7KHIROORZLQJ,64/FRPPDQGVFDQQRWEHSURFHVVHGE\'64/%/2%'803(',7(;,7
+(/3,138728738748,76(76(7$872''/6(7%/2%',63/$<6(7&28176(7
(&+26(7/,676(71$0(66(73/$16(767$766(77(506(77,0(6+(//6+2:
&+(&.6+2:'$7$%$6(6+2:'20$,166+2:(;&(37,2166+2:),/7(566+2:
)81&7,2166+2:*(1(5$72566+2:*5$176+2:,1'(;6+2:352&('85(6
6+2:6<67(06+2:7$%/(66+2:75,**(566+2:9(56,216+2:9,(:6

248 INTERBASE 5
WRITING A DSQL APPLICATION

SQL character strings


:LWKLQD'64/DSSOLFDWLRQDQ64/VWDWHPHQWFDQFRPHIURPGLIIHUHQWVRXUFHV,WFDQFRPH
GLUHFWO\IURPDXVHUZKRHQWHUVDVWDWHPHQWDWDSURPSWDVGRHVisql2ULWFDQEHJHQHUDWHG
E\WKHDSSOLFDWLRQLQUHVSRQVHWRXVHULQWHUDFWLRQ:KDWHYHUWKHVRXUFHRIWKH64/VWDWHPHQW
LWPXVWEHUHSUHVHQWHGDVDQ64/VWDWHPHQWVWULQJDFKDUDFWHUVWULQJWKDWLVSDVVHGWR'64/IRU
SURFHVVLQJ
%HFDXVH64/VWDWHPHQWVWULQJVDUH&FKDUDFWHUVWULQJVWKDWDUHSURFHVVHGGLUHFWO\E\'64/
WKH\FDQQRWEHJLQZLWKWKH(;(&64/SUHIL[RUHQGZLWKDVHPLFRORQ  7KHVHPLFRORQLV
RIFRXUVHWKHDSSURSULDWHWHUPLQDWRUIRUWKH&VWULQJGHFODUDWLRQLWVHOI)RUH[DPSOHWKH
IROORZLQJKRVWODQJXDJHYDULDEOHGHFODUDWLRQLVDYDOLG64/VWDWHPHQWVWULQJ
char *str = "DELETE FROM CUSTOMER WHERE CUST_NO = 256";

Value parameters in statement strings


64/VWDWHPHQWVWULQJVRIWHQLQFOXGHYDOXHSDUDPHWHUVH[SUHVVLRQVWKDWHYDOXDWHWRDVLQJOH
QXPHULFRUFKDUDFWHUYDOXH3DUDPHWHUVFDQEHXVHGDQ\ZKHUHLQVWDWHPHQWVWULQJVZKHUH64/
H[SHFWVDYDOXHWKDWLVQRWWKHQDPHRIDGDWDEDVHREMHFW
$YDOXHSDUDPHWHULQDVWDWHPHQWVWULQJFDQEHSDVVHGDVDFRQVWDQWRUSDVVHGDVDSODFHKROGHU
DWUXQWLPH)RUH[DPSOHWKHIROORZLQJVWDWHPHQWVWULQJSDVVHVDVDFRQVWDQW
char *str = "DELETE FROM CUSTOMER WHERE CUST_NO = 256";

,WLVDOVRSRVVLEOHWREXLOGVWULQJVDWUXQWLPHIURPDFRPELQDWLRQRIFRQVWDQWV7KLVPHWKRG
LVXVHIXOIRUVWDWHPHQWVZKHUHWKHYDULDEOHLVQRWDWUXHFRQVWDQWRULWLVDWDEOHRUFROXPQ
QDPHDQGZKHUHWKHVWDWHPHQWLVH[HFXWHGRQO\RQFHLQWKHDSSOLFDWLRQ
7RSDVVDSDUDPHWHUDVDSODFHKROGHUWKHYDOXHLVSDVVHGDVDTXHVWLRQPDUN " HPEHGGHG
ZLWKLQWKHVWDWHPHQWVWULQJ
char *str = "DELETE FROM CUSTOMER WHERE CUST_NO = ?";

:KHQ'64/SURFHVVHVDVWDWHPHQWFRQWDLQLQJDSODFHKROGHULWUHSODFHVWKHTXHVWLRQPDUN
ZLWKDYDOXHVXSSOLHGLQWKH;64/'$8VHSODFHKROGHUVLQVWDWHPHQWVWKDWDUHSUHSDUHGRQFH
EXWH[HFXWHGPDQ\WLPHVZLWKGLIIHUHQWSDUDPHWHUYDOXHV
5HSODFHDEOHYDOXHSDUDPHWHUVDUHRIWHQXVHGWRVXSSO\YDOXHVLQ:+(5(FODXVHFRPSDULVRQV
DQGLQWKH83'$7(VWDWHPHQW6(7FODXVH

PROGRAMMER’S GUIDE 249


CHAPTER 14 USING DYNAMIC SQL

Understanding the XSQLDA


$OO'64/DSSOLFDWLRQVPXVWGHFODUHRQHRUPRUHH[WHQGHG64/GHVFULSWRUDUHDV ;64/'$V 
7KH;64/'$VWUXFWXUHGHILQLWLRQFDQEHIRXQGLQWKHLEDVHKKHDGHUILOHLQWKH,QWHU%DVH
LQFOXGHGLUHFWRU\$SSOLFDWLRQVGHFODUHLQVWDQFHVRIWKH;64/'$IRUXVH
7KH;64/'$LVDKRVWODQJXDJHGDWDVWUXFWXUHWKDW'64/XVHVWRWUDQVSRUWGDWDWRRUIURP
DGDWDEDVHZKHQSURFHVVLQJDQ64/VWDWHPHQWVWULQJ7KHUHDUHWZRW\SHVRI;64/'$VLQSXW
GHVFULSWRUVDQGRXWSXWGHVFULSWRUV%RWKLQSXWDQGRXWSXWGHVFULSWRUVDUHLPSOHPHQWHGXVLQJ
WKH;64/'$VWUXFWXUH
2QHILHOGLQWKH;64/'$WKH;64/9$5LVHVSHFLDOO\LPSRUWDQWEHFDXVHRQH;64/9$5PXVW
EHGHILQHGIRUHDFKLQSXWSDUDPHWHURUFROXPQUHWXUQHG/LNHWKH;64/'$WKH;64/9$5LV
DVWUXFWXUHGHILQHGLQLEDVHKLQWKH,QWHU%DVHLQFOXGHGLUHFWRU\
$SSOLFDWLRQVGRQRWGHFODUHLQVWDQFHVRIWKH;64/9$5DKHDGRIWLPHEXWPXVWLQVWHDG
G\QDPLFDOO\DOORFDWHVWRUDJHIRUWKHSURSHUQXPEHURI;64/9$5VWUXFWXUHVUHTXLUHGIRUHDFK
'64/VWDWHPHQWEHIRUHLWLVH[HFXWHGWKHQGHDOORFDWHLWDVDSSURSULDWHDIWHUVWDWHPHQW
H[HFXWLRQ
7KHIROORZLQJILJXUHLOOXVWUDWHVWKHUHODWLRQVKLSEHWZHHQWKH;64/'$DQGWKH;64/9$5

250 INTERBASE 5
UNDERSTANDING THE XSQLDA

FIGURE 14.1 XSQLDA and XSQLVAR relationship

Single instance of XSQLDA

short version
char sqldaid[8]
ISC_LONG sqldabc
short sqln
short sqld
XSQLVAR sqlvar[n]

Array of n instances of XSQLVAR

1st instance nth instance


short sqltype short sqltype
short sqlscale short sqlscale
short sqlsubtype short sqlsubtype
short sqllen short sqllen
char *sqldata char *sqldata
short *sqlind short *sqlind
short sqlname_length short sqlname_length
char sqlname[32] char sqlname[32]
short relname_length short relname_length
char relname[32] char relname[32]
short ownname_length short ownname_length
char ownname[32] char ownname[32]
short aliasname_length short aliasname_length
char aliasname[32] char aliasname[32]

$QLQSXW;64/'$FRQVLVWVRIDVLQJOH;64/'$VWUXFWXUHDQGRQH;64/9$5VWUXFWXUH
IRUHDFKLQSXWSDUDPHWHU$QRXWSXW;64/'$DOVRFRQVLVWVRIRQH;64/'$VWUXFWXUHDQG
RQH;64/9$5VWUXFWXUHIRUHDFKGDWDLWHPUHWXUQHGE\WKHVWDWHPHQW$Q;64/'$DQGLWV
DVVRFLDWHG;64/9$5VWUXFWXUHVDUHDOORFDWHGDVDVLQJOHEORFNRIFRQWLJXRXVPHPRU\

PROGRAMMER’S GUIDE 251


CHAPTER 14 USING DYNAMIC SQL

7KH35(3$5(DQG'(6&5,%(VWDWHPHQWVFDQEHXVHGWRGHWHUPLQHWKHSURSHUQXPEHURI
;64/9$5VWUXFWXUHVWRDOORFDWHDQGWKH;64/'$B/(1*7+PDFURFDQEHXVHGWRDOORFDWHWKH
SURSHUDPRXQWRIVSDFH)RUPRUHLQIRUPDWLRQDERXWWKH;64/'$B/(1*7+PDFURVHH
´8VLQJWKH;64/'$B/(1*7+PDFURµRQSDJH 

XSQLDA field descriptions


7KHIROORZLQJWDEOHGHVFULEHVWKHILHOGVWKDWFRPSULVHWKH;64/'$VWUXFWXUH

Field definition Description


short version Indicates the version of the XSQLDA structure. Set by an application. The current version
is defined in ibase.h as SQLDA_VERSION1.
char sqldaid[8] Reserved for future use.
ISC_LONG sqldabc Reserved for future use.
short sqln Indicates the number of elements in the sqlvar array. Set by the application. Whenever the
application allocates storage for a descriptor, it should set this field.
short sqld Indicates the number of parameters (for an input XSQLDA), or the number of select-list
items (for an output XSQLDA). Set by InterBase during a DESCRIBE or PREPARE.
For an input descriptor, an sqld of 0 indicates that the SQL statement has no parameters.
For an output descriptor, an sqld of 0 indicates that the SQL statement is not a SELECT
statement.
XSQLVAR sqlvar The array of XSQLVAR structures. The number of elements in the array is specified in the
sqln field.
TABLE 14.1 XSQLDA field descriptions

252 INTERBASE 5
UNDERSTANDING THE XSQLDA

XSQLVAR field descriptions


7KHIROORZLQJWDEOHGHVFULEHVWKHILHOGVWKDWFRPSULVHWKH;64/9$5VWUXFWXUH

Field definition Description


short sqltype Indicates the SQL datatype of parameters or select-list items. Set by InterBase during
PREPARE or DESCRIBE.
short sqlscale Provides scale, specified as a negative number, for exact numeric datatypes (DECIMAL,
NUMERIC). Set by InterBase during PREPARE or DESCRIBE.
short sqlsubtype Specifies the subtype for Blob data. Set by InterBase during PREPARE or DESCRIBE.
short sqllen Indicates the maximum size, in bytes, of data in the sqldata field. Set by InterBase
during PREPARE or DESCRIBE.
char *sqldata For input descriptors, specifies either the address of a select-list item or a parameter.
Set by the application.
For output descriptors, contains a value for a select-list item. Set by InterBase.
short *sqlind On input, specifies the address of an indicator variable. Set by an application.
On output, specifies the address of column indicator value for a select-list item
following a FETCH. A value of 0 indicates that the column is not NULL; a value of –1
indicates the column is NULL. Set by InterBase.
short Specifies the length, in bytes, of the data in field, sqlname. Set by InterBase during
sqlname_length DESCRIBE OUTPUT.
char sqlname[32] Contains the name of the column. Not null (\0) terminated. Set by InterBase during
DESCRIBE OUTPUT.
short Specifies the length, in bytes, of the data in field, relname. Set by InterBase during
relname_length DESCRIBE OUTPUT.
TABLE 14.2 XSQLVAR field descriptions

PROGRAMMER’S GUIDE 253


CHAPTER 14 USING DYNAMIC SQL

Field definition Description


char relname[32] Contains the name of the table. Not null (\0) terminated. Set by InterBase during
DESCRIBE OUTPUT.
short Specifies the length, in bytes, of the data in field, ownname. Set by InterBase during
ownname_length DESCRIBE OUTPUT.
char ownname[32] Contains the owner name of the table. Not null (\0) terminated. Set by InterBase
during DESCRIBE OUTPUT.
short Specifies the length, in bytes, of the data in field, aliasname. Set by InterBase during
aliasname_length DESCRIBE OUTPUT.
char aliasname[32] Contains the alias name of the column. If no alias exists, contains the column name.
Not null (\0) terminated. Set by InterBase during DESCRIBE OUTPUT.
TABLE 14.2 XSQLVAR field descriptions (continued)

Input descriptors
,QSXWGHVFULSWRUVSURFHVV64/VWDWHPHQWVWULQJVWKDWFRQWDLQSDUDPHWHUV%HIRUHDQ
DSSOLFDWLRQFDQH[HFXWHDVWDWHPHQWZLWKSDUDPHWHUVLWPXVWVXSSO\YDOXHVIRUWKHP7KH
DSSOLFDWLRQLQGLFDWHVWKHQXPEHURISDUDPHWHUVSDVVHGLQWKH;64/'$VTOGILHOGWKHQ
GHVFULEHVHDFKSDUDPHWHULQDVHSDUDWH;64/9$5VWUXFWXUH)RUH[DPSOHWKHIROORZLQJ
VWDWHPHQWVWULQJFRQWDLQVWZRSDUDPHWHUVVRDQDSSOLFDWLRQPXVWVHWVTOGWRDQGGHVFULEH
HDFKSDUDPHWHU
char *str = "UPDATE DEPARTMENT SET BUDGET = ? WHERE LOCATION = ?";

:KHQWKHVWDWHPHQWLVH[HFXWHGWKHILUVW;64/9$5VXSSOLHVLQIRUPDWLRQDERXWWKH%8'*(7
YDOXHDQGWKHVHFRQG;64/9$5VXSSOLHVWKH/2&$7,21YDOXH
)RUPRUHLQIRUPDWLRQDERXWXVLQJLQSXWGHVFULSWRUVVHH´'64/SURJUDPPLQJPHWKRGVµRQ
SDJH 

Output descriptors
2XWSXWGHVFULSWRUVUHWXUQYDOXHVIURPDQH[HFXWHGTXHU\WRDQDSSOLFDWLRQ7KHVTOGILHOGRI
WKH;64/'$LQGLFDWHVKRZPDQ\YDOXHVZHUHUHWXUQHG(DFKYDOXHLVVWRUHGLQDVHSDUDWH
;64/9$5VWUXFWXUH7KH;64/'$VTOYDUILHOGSRLQWVWRWKHILUVWRIWKHVH;64/9$5VWUXFWXUHV
7KHIROORZLQJVWDWHPHQWVWULQJUHTXLUHVDQRXWSXWGHVFULSWRU
char *str = "SELECT * FROM CUSTOMER WHERE CUST_NO > 100";

254 INTERBASE 5
UNDERSTANDING THE XSQLDA

)RULQIRUPDWLRQDERXWUHWULHYLQJLQIRUPDWLRQIURPDQRXWSXWGHVFULSWRUVHH´'64/
SURJUDPPLQJPHWKRGVµRQSDJH 

Using the XSQLDA_LENGTH macro


7KHLEDVHKKHDGHUILOHGHILQHVDPDFUR;64/'$B/(1*7+WRFDOFXODWHWKHQXPEHURIE\WHV
WKDWPXVWEHDOORFDWHGIRUDQLQSXWRURXWSXW;64/'$;64/'$B/(1*7+LVGHILQHGDV
IROORZV
#define XSQLDA_LENGTH (n) (sizeof (XSQLDA) + (n - 1) * sizeof(XSQLVAR))

QLVWKHQXPEHURISDUDPHWHUVLQDVWDWHPHQWVWULQJRUWKHQXPEHURIVHOHFWOLVWLWHPV
UHWXUQHGIURPDTXHU\)RUH[DPSOHWKHIROORZLQJ&VWDWHPHQWXVHVWKH;64/'$B/(1*7+
PDFURWRVSHFLI\KRZPXFKPHPRU\WRDOORFDWHIRUDQ;64/'$ZLWKSDUDPHWHUVRUUHWXUQ
LWHPV
XSQLDA *my_xsqlda;
. . .
my_xsqlda = (XSQLDA *) malloc(XSQLDA_LENGTH(5));
. . .

)RUPRUHLQIRUPDWLRQDERXWXVLQJWKH;64/'$B/(1*7+PDFURVHH´'64/SURJUDPPLQJ
PHWKRGVµRQSDJH 

PROGRAMMER’S GUIDE 255


CHAPTER 14 USING DYNAMIC SQL

SQL datatype macro constants


,QWHU%DVHGHILQHVDVHWRIPDFURFRQVWDQWVWRUHSUHVHQW64/GDWDW\SHVDQG18//VWDWXV
LQIRUPDWLRQLQDQ;64/9$5$QDSSOLFDWLRQVKRXOGXVHWKHVHPDFURFRQVWDQWVWRVSHFLI\WKH
GDWDW\SHRISDUDPHWHUVDQGWRGHWHUPLQHWKHGDWDW\SHVRIVHOHFWOLVWLWHPVLQDQ64/
VWDWHPHQW7KHIROORZLQJWDEOHOLVWVHDFK64/GDWDW\SHLWVFRUUHVSRQGLQJPDFURFRQVWDQW
H[SUHVVLRQ&GDWDW\SHRU,QWHU%DVHW\SHGHIDQGZKHWKHURUQRWWKHVTOLQGILHOGLVXVHGWR
LQGLFDWHDSDUDPHWHURUYDULDEOHWKDWFRQWDLQV18//RUXQNQRZQGDWD

sqlin
d
used
SQL datatype Macro expression C datatype or typedef ?
Array SQL_ARRAY ISC_QUAD No
Array SQL_ARRAY + 1 ISC_QUAD Yes
Blob SQL_BLOB ISC_QUAD No
Blob SQL_BLOB + 1 ISC_QUAD Yes
CHAR SQL_TEXT char[ ] No
CHAR SQL_TEXT + 1 char[ ] Yes
DATE SQL_DATE ISC_QUAD No
DATE SQL_DATE + 1 ISC_QUAD Yes
DECIMAL SQL_SHORT, SQL_LONG, or int, long, or double No
QL_DOUBLE

DECIMAL SQL_SHORT + 1, SQL_LONG + 1, int, long, or double Yes


or SQL_DOUBLE + 1
DOUBLE PRECISON SQL_DOUBLE double No
DOUBLE PRECISION SQL_DOUBLE + 1 double Yes
INTEGER SQL_LONG long No
INTEGER SQL_LONG + 1 long Yes
FLOAT SQL_FLOAT float No
TABLE 14.3 SQL datatypes, macro expressions, and C datatypes

256 INTERBASE 5
UNDERSTANDING THE XSQLDA

sqlin
d
used
SQL datatype Macro expression C datatype or typedef ?
FLOAT SQL_FLOAT + 1 float Yes
NUMERIC SQL_SHORT, SQL_LONG, int, long, or double No
or SQL_DOUBLE
NUMERIC SQL_SHORT + 1, SQL_LONG + 1, int, long, or double Yes
or SQL_DOUBLE + 1
SMALLINT SQL_SHORT short No
SMALLINT SQL_SHORT + 1 short Yes
VARCHAR SQL_VARYING First 2 bytes: short containing No
the length of the character string.
Remaining bytes: char[ ]
VARCHAR SQL_VARYING + 1 First 2 bytes: short containing Yes
the length of the character string.
Remaining bytes: char[ ]
TABLE 14.3 SQL datatypes, macro expressions, and C datatypes (continued)

Note '(&,0$/DQG180(5,&GDWDW\SHVDUHVWRUHGLQWHUQDOO\DV60$//,17,17(*(5RU
'28%/(35(&,6,21GDWDW\SHV7RVSHFLI\WKHFRUUHFWPDFURH[SUHVVLRQWRSURYLGHIRUD
'(&,0$/RU180(5,&FROXPQXVHisqlWRH[DPLQHWKHFROXPQGHILQLWLRQLQWKHWDEOHWRVHH
KRZ,QWHU%DVHLVVWRULQJFROXPQGDWDWKHQFKRRVHDFRUUHVSRQGLQJPDFURH[SUHVVLRQ
7KHGDWDW\SHLQIRUPDWLRQIRUDSDUDPHWHURUVHOHFWOLVWLWHPLVFRQWDLQHGLQWKHVTOW\SHILHOGRI
WKH;64/9$5VWUXFWXUH7KHYDOXHFRQWDLQHGLQWKHVTOW\SHILHOGSURYLGHVWZRSLHFHVRI
LQIRUPDWLRQ
g 7KHGDWDW\SHRIWKHSDUDPHWHURUVHOHFWOLVWLWHP
g :KHWKHUVTOLQGLVXVHGWRLQGLFDWH18//YDOXHV,IVTOLQGLVXVHGLWVYDOXHVSHFLILHVZKHWKHUWKH
SDUDPHWHURUVHOHFWOLVWLWHPLV18// ² RUQRW18//  
)RUH[DPSOHLIWKHVTOW\SHILHOGHTXDOV64/B7(;7WKHSDUDPHWHURUVHOHFWOLVWLWHPLVD&+$5
WKDWGRHVQRWXVHVTOLQGWRFKHFNIRUD18//YDOXH EHFDXVHLQWKHRU\18//YDOXHVDUHQRW
DOORZHGIRULW ,IVTOW\SHHTXDOV64/B7(;7WKHQVTOLQGFDQEHFKHFNHGWRVHHLIWKH
SDUDPHWHURUVHOHFWOLVWLWHPLV18//

PROGRAMMER’S GUIDE 257


CHAPTER 14 USING DYNAMIC SQL

7,3 7KH&ODQJXDJHH[SUHVVLRQsqltype & 1SURYLGHVDXVHIXOWHVWRIZKHWKHUDSDUDPHWHURU


VHOHFWOLVWLWHPFDQFRQWDLQD18//7KHH[SUHVVLRQHYDOXDWHVWRLIWKHSDUDPHWHURU
VHOHFWOLVWLWHPFDQQRWFRQWDLQD18//DQGLIWKHSDUDPHWHURUVHOHFWOLVWLWHPFDQFRQWDLQ
D18//7KHIROORZLQJFRGHIUDJPHQWGHPRQVWUDWHVKRZWRXVHWKHH[SUHVVLRQ
if (sqltype & 1 == 0)
{
/* parameter or select-list item that CANNOT contain a NULL */
}
else
{
/* parameter or select-list item CAN contain a NULL */
}

%\GHIDXOWERWK35(3$5(,172DQG'(6&5,%(UHWXUQDPDFURH[SUHVVLRQRIW\SHVR
WKHVTOLQGVKRXOGDOZD\VEHH[DPLQHGIRU18//YDOXHVZLWKWKHVHVWDWHPHQWV

Handling varying string datatypes


9$5&+$5&+$5$&7(59$5<,1*DQG1&+$59$5<,1*GDWDW\SHVUHTXLUHFDUHIXOKDQGOLQJ
LQ'64/7KHILUVWWZRE\WHVRIWKHVHGDWDW\SHVFRQWDLQVWULQJOHQJWKLQIRUPDWLRQZKLOHWKH
UHPDLQGHURIWKHGDWDFRQWDLQVWKHDFWXDOE\WHVRIVWULQJGDWDWRSURFHVV
7RDYRLGKDYLQJWRZULWHFRGHWRH[WUDFWDQGSURFHVVYDULDEOHOHQJWKVWULQJVLQDQDSSOLFDWLRQ
LWLVSRVVLEOHWRIRUFHWKHVHGDWDW\SHVWRIL[HGOHQJWKXVLQJ64/PDFURH[SUHVVLRQV)RUPRUH
LQIRUPDWLRQDERXWIRUFLQJYDULDEOHOHQJWKGDWDWRIL[HGOHQJWKIRUSURFHVVLQJVHH´&RHUFLQJ
GDWDW\SHVµRQSDJH 
$SSOLFDWLRQVFDQLQVWHDGGHWHFWDQGSURFHVVYDULDEOHOHQJWKGDWDGLUHFWO\7RGRVRWKH\PXVW
H[WUDFWWKHILUVWWZRE\WHVIURPWKHVWULQJWRGHWHUPLQHWKHE\WHOHQJWKRIWKHVWULQJLWVHOI
WKHQUHDGWKHVWULQJE\WHE\E\WHLQWRDQXOOWHUPLQDWHGEXIIHU

NUMERIC and DECIMAL datatypes


'(&,0$/DQG180(5,&GDWDW\SHVDUHVWRUHGLQWHUQDOO\DV60$//,17,17(*(5RU
'28%/(35(&,6,21GDWDW\SHVGHSHQGLQJRQWKHSUHFLVLRQDQGVFDOHGHILQHGIRUDFROXPQ
GHILQLWLRQWKDWXVHVWKHVHW\SHV7RGHWHUPLQHKRZD'(&,0$/RU180(5,&YDOXHLVDFWXDOO\
VWRUHGLQWKHGDWDEDVHXVHisqlWRH[DPLQHWKHFROXPQGHILQLWLRQLQWKHWDEOH,I180(5,&LV
UHSRUWHGWKHQGDWDLVDFWXDOO\EHLQJVWRUHGDV'28%/(35(&,6,21

258 INTERBASE 5
UNDERSTANDING THE XSQLDA

:KHQD'(&,0$/RU180(5,&YDOXHLVVWRUHGDVD60$//,17RU,17(*(5WKHYDOXHLV
VWRUHGDVDZKROHQXPEHU'XULQJUHWULHYDOLQ'64/WKHVTOVFDOHILHOGRIWKH;64/9$5LVVHW
WRDQHJDWLYHQXPEHUWKDWLQGLFDWHVWKHIDFWRURIWHQE\ZKLFKWKHZKROHQXPEHU UHWXUQHG
LQVTOGDWD PXVWEHGLYLGHGLQRUGHUWRSURGXFHWKHFRUUHFW180(5,&RU'(&,0$/YDOXHZLWK
LWVIUDFWLRQDOSDUW,IVTOFDOHLV²WKHQWKHQXPEHUPXVWEHGLYLGHGE\LILWLV²WKHQWKH
QXPEHUPXVWEHGLYLGHGE\²E\DQGVRIRUWK

Coercing datatypes
6RPHWLPHVZKHQSURFHVVLQJ'64/LQSXWSDUDPHWHUVDQGVHOHFWOLVWLWHPVLWLVGHVLUDEOHRU
QHFHVVDU\WRWUDQVODWHRQHGDWDW\SHWRDQRWKHU7KLVSURFHVVLVUHIHUUHGWRDVGDWDW\SHFRHUFLRQ
)RUH[DPSOHGDWDW\SHFRHUFLRQLVRIWHQXVHGZKHQSDUDPHWHUVRUVHOHFWOLVWLWHPVDUHRIW\SH
9$5&+$57KHILUVWWZRE\WHVRI9$5&+$5GDWDFRQWDLQVWULQJOHQJWKLQIRUPDWLRQZKLOHWKH
UHPDLQGHURIWKHGDWDLVWKHVWULQJWRSURFHVV%\FRHUFLQJWKHGDWDIURP64/B9$5<,1*WR
64/B7(;7GDWDSURFHVVLQJFDQEHVLPSOLILHG
&RHUFLRQFDQRQO\EHIURPRQHFRPSDWLEOHGDWDW\SHWRDQRWKHU)RUH[DPSOH64/B9$5<,1*
WR64/B7(;7RU64/B6+257WR64/B/21*

4 &RHUFLQJFKDUDFWHUGDWDW\SHV
7RFRHUFH64/B9$5<,1*GDWDW\SHVWR64/B7(;7GDWDW\SHVFKDQJHWKHVTOW\SHILHOGLQWKH
SDUDPHWHU·VRUVHOHFWOLVWLWHP·V;64/9$5VWUXFWXUHWRWKHGHVLUHG64/PDFURGDWDW\SH
FRQVWDQW)RUH[DPSOHWKHIROORZLQJVWDWHPHQWDVVXPHVWKDWYDULVDSRLQWHUWRDQ;64/9$5
VWUXFWXUHDQGWKDWLWFRQWDLQVDQ64/B9$5<,1*GDWDW\SHWRFRQYHUWWR64/B7(;7
var->sqltype = SQL_TEXT;

$IWHUFRHUFLQJDFKDUDFWHUGDWDW\SHSURYLGHSURSHUVWRUDJHVSDFHIRULW7KH;64/9$5ILHOG
VTOOHQFRQWDLQVLQIRUPDWLRQDERXWWKHVL]HRIWKHXQFRHUFHGGDWD6HWWKH;64/9$5VTOGDWD
ILHOGWRWKHDGGUHVVRIWKHGDWD

4 &RHUFLQJQXPHULFGDWDW\SHV
7RFRHUFHRQHQXPHULFGDWDW\SHWRDQRWKHUFKDQJHWKHVTOW\SHILHOGLQWKHSDUDPHWHU·VRU
VHOHFWOLVWLWHP·V;64/9$5VWUXFWXUHWRWKHGHVLUHG64/PDFURGDWDW\SHFRQVWDQW)RU
H[DPSOHWKHIROORZLQJVWDWHPHQWDVVXPHVWKDWYDULVDSRLQWHUWRDQ;64/9$5VWUXFWXUHDQG
WKDWLWFRQWDLQVDQ64/B6+257GDWDW\SHWRFRQYHUWWR64/B/21*
var->sqltype = SQL_LONG;

,03257$17 'RQRWFRHUFHDODUJHUGDWDW\SHWRDVPDOOHURQH'DWDFDQEHORVWLQVXFKDWUDQVODWLRQ

PROGRAMMER’S GUIDE 259


CHAPTER 14 USING DYNAMIC SQL

4 6HWWLQJD18//LQGLFDWRU
,IDSDUDPHWHURUVHOHFWOLVWLWHPFDQFRQWDLQD18//YDOXHWKHVTOLQGILHOGLVXVHGWRLQGLFDWH
LWV18//VWDWXV$SSURSULDWHVWRUDJHVSDFHPXVWEHDOORFDWHGIRUVTOLQGEHIRUHYDOXHVFDQEH
VWRUHGWKHUH
2QLQVHUWLRQVHWVTOLQGWR²WRLQGLFDWHWKDW18//YDOXHVDUHOHJDO2WKHUZLVHVHWVTOLQGWR
2QVHOHFWLRQDQVTOLQGRI²LQGLFDWHVDILHOGFRQWDLQVD18//YDOXH2WKHUYDOXHVLQGLFDWHD
ILHOGFRQWDLQVQRQ18//GDWD

Aligning numerical data


2UGLQDULO\ZKHQDYDULDEOHZLWKDQXPHULFGDWDW\SHLVFUHDWHGWKHFRPSLOHUZLOOHQVXUHWKDW
WKHYDULDEOHLVVWRUHGDWDSURSHUO\DOLJQHGDGGUHVVEXWZKHQQXPHULFGDWDLVVWRUHGLQD
G\QDPLFDOO\DOORFDWHGEXIIHUVSDFHVXFKDVFDQEHSRLQWHGWRE\WKH;64/'$DQG;64/9$5
VWUXFWXUHVWKHSURJUDPPHUPXVWWDNHSUHFDXWLRQVWRHQVXUHWKDWWKHVWRUDJHVSDFHLVSURSHUO\
DOLJQHG
&HUWDLQSODWIRUPVLQSDUWLFXODUWKRVHZLWK5,6&SURFHVVRUVUHTXLUHWKDWQXPHULFGDWDLQ
G\QDPLFDOO\DOORFDWHGVWRUDJHVWUXFWXUHVEHDOLJQHGSURSHUO\LQPHPRU\$OLJQPHQWLV
GHSHQGHQWERWKRQGDWDW\SHDQGSODWIRUP
)RUH[DPSOHDVKRUWLQWHJHURQD6XQ63$5&VWDWLRQPXVWEHORFDWHGDWDQDGGUHVVGLYLVLEOH
E\ZKLOHDORQJRQWKHVDPHSODWIRUPPXVWEHORFDWHGDWDQDGGUHVVGLYLVLEOHE\,QPRVW
FDVHVDGDWDLWHPLVSURSHUO\DOLJQHGLIWKHDGGUHVVRILWVVWDUWLQJE\WHLVGLYLVLEOHE\WKHFRUUHFW
DOLJQPHQWQXPEHU&RQVXOWVSHFLILFV\VWHPDQGFRPSLOHUGRFXPHQWDWLRQIRUDOLJQPHQW
UHTXLUHPHQWV
$XVHIXOUXOHRIWKXPELVWKDWWKHVL]HRIDGDWDW\SHLVDOZD\VDYDOLGDOLJQPHQWQXPEHUIRU
WKHGDWDW\SH)RUDJLYHQW\SH7LIVL]HRI 7 HTXDOVQWKHQDGGUHVVHVGLYLVLEOHE\QDUH
FRUUHFWO\DOLJQHGIRU77KHIROORZLQJPDFURH[SUHVVLRQFDQEHXVHGWRDOLJQGDWD
#define ALIGN(ptr, n) ((ptr + n - 1) & ~(n - 1))

ZKHUHSWULVDSRLQWHUWRFKDU
7KHIROORZLQJFRGHLOOXVWUDWHVKRZWKH$/,*1PDFURPLJKWEHXVHG
char *buffer_pointer, *next_aligned;
next_aligned = ALIGN(buffer_pointer, sizeof(T));

260 INTERBASE 5
DSQL PROGRAMMING METHODS

DSQL programming methods


7KHUHDUHIRXUSRVVLEOH'64/SURJUDPPLQJPHWKRGVIRUKDQGOLQJDQ64/VWDWHPHQWVWULQJ
7KHEHVWPHWKRGIRUSURFHVVLQJDVWULQJGHSHQGVRQWKHW\SHRI64/VWDWHPHQWLQWKHVWULQJ
DQGZKHWKHURUQRWLWFRQWDLQVSODFHKROGHUVIRUSDUDPHWHUV7KHIROORZLQJGHFLVLRQWDEOH
H[SODLQVKRZWRGHWHUPLQHWKHDSSURSULDWHSURFHVVLQJPHWKRGIRUDJLYHQVWULQJ

Does it have Processing method to


Is it a query? placeholders? use
No No Method 1
No Yes Method 2
Yes No Method 3
Yes Yes Method 4
TABLE 14.4 SQL statement strings and recommended processing methods

Method 1: Non-query statements without parameters


7KHUHDUHWZRZD\VWRSURFHVVDQ64/VWDWHPHQWVWULQJFRQWDLQLQJDQRQTXHU\VWDWHPHQW
ZLWKRXWSODFHKROGHUSDUDPHWHUV
g 8VH(;(&87(,00(',$7(WRSUHSDUHDQGH[HFXWHWKHVWULQJDVLQJOHWLPH
g 8VH35(3$5(WRSDUVHWKHVWDWHPHQWIRUH[HFXWLRQDQGDVVLJQLWDQDPHWKHQXVH(;(&87(
WRFDUU\RXWWKHVWDWHPHQW·VDFWLRQVDVPDQ\WLPHVDVUHTXLUHGLQDQDSSOLFDWLRQ

4 8VLQJ(;(&87(,00(',$7(
 7RH[HFXWHDVWDWHPHQWVWULQJDVLQJOHWLPHXVH(;(&87(,00(',$7(
 (OLFLWDVWDWHPHQWVWULQJIURPWKHXVHURUFUHDWHRQHWKDWFRQWDLQVWKH64/
VWDWHPHQWWREHSURFHVVHG)RUH[DPSOHWKHIROORZLQJVWDWHPHQWFUHDWHVDQ64/
VWDWHPHQWVWULQJ
char *str = "UPDATE DEPARTMENT SET BUDGET = BUDGET * 1.05";

 3DUVHDQGH[HFXWHWKHVWDWHPHQWVWULQJXVLQJ(;(&87(,00(',$7(
EXEC SQL
EXECUTE IMMEDIATE :str;
Note (;(&87(,00(',$7(DOVRDFFHSWVVWULQJOLWHUDOV)RUH[DPSOH
EXEC SQL

PROGRAMMER’S GUIDE 261


CHAPTER 14 USING DYNAMIC SQL

EXECUTE IMMEDIATE
"UPDATE DEPARTMENT SET BUDGET = BUDGET * 1.05";

4 8VLQJ35(3$5(DQG(;(&87(
7RH[HFXWHDVWDWHPHQWVWULQJVHYHUDOWLPHVXVH35(3$5(DQG(;(&87(
 (OLFLWDVWDWHPHQWVWULQJIURPWKHXVHURUFUHDWHRQHWKDWFRQWDLQVWKH64/
VWDWHPHQWWREHSURFHVVHG)RUH[DPSOHWKHIROORZLQJVWDWHPHQWFUHDWHVDQ64/
VWDWHPHQWVWULQJ
char *str = "UPDATE DEPARTMENT SET BUDGET = BUDGET * 1.05";

 3DUVHDQGQDPHWKHVWDWHPHQWVWULQJZLWK35(3$5(7KHQDPHLVXVHGLQ
VXEVHTXHQWFDOOVWR(;(&87(
EXEC SQL
PREPARE SQL_STMT FROM :str;

64/B6707LVWKHQDPHDVVLJQHGWRWKHSDUVHGVWDWHPHQWVWULQJ
 ([HFXWHWKHQDPHGVWDWHPHQWVWULQJXVLQJ(;(&87()RUH[DPSOHWKHIROORZLQJ
VWDWHPHQWH[HFXWHVDVWDWHPHQWVWULQJQDPHG64/B6707
EXEC SQL
EXECUTE SQL_STMT;

Note 35(3$5(DOVRDFFHSWVVWULQJOLWHUDOV)RUH[DPSOH
EXEC SQL
PREPARE SQL_STMT FROM
"UPDATE DEPARTMENT SET BUDGET = BUDGET * 1.05";

2QFHDVWDWHPHQWVWULQJLVSUHSDUHGLWFDQEHH[HFXWHGDVPDQ\WLPHVDVUHTXLUHGLQDQ
DSSOLFDWLRQ

Method 2: Non-query statements with parameters


7KHUHDUHWZRVWHSVWRSURFHVVLQJDQ64/VWDWHPHQWVWULQJFRQWDLQLQJDQRQTXHU\VWDWHPHQW
ZLWKSODFHKROGHUSDUDPHWHUV
 &UHDWLQJDQLQSXW;64/'$WRSURFHVVDVWDWHPHQWVWULQJ·VSDUDPHWHUV
 3UHSDULQJDQGH[HFXWLQJWKHVWDWHPHQWVWULQJZLWKLWVSDUDPHWHUV

262 INTERBASE 5
DSQL PROGRAMMING METHODS

4 &UHDWLQJWKHLQSXW;64/'$
3ODFHKROGHUSDUDPHWHUVDUHUHSODFHGZLWKDFWXDOGDWDEHIRUHDSUHSDUHG64/VWDWHPHQWVWULQJ
LVH[HFXWHG%HFDXVHWKRVHSDUDPHWHUVDUHXQNQRZQZKHQWKHVWDWHPHQWVWULQJLVFUHDWHGDQ
LQSXW;64/'$PXVWEHFUHDWHGWRVXSSO\SDUDPHWHUYDOXHVDWH[HFXWHWLPH7RSUHSDUHWKH
;64/'$IROORZWKHVHVWHSV
 'HFODUHDYDULDEOHWRKROGWKH;64/'$QHHGHGWRSURFHVVSDUDPHWHUV)RU
H[DPSOHWKHIROORZLQJGHFODUDWLRQFUHDWHVDQ;64/'$FDOOHGLQBVTOGD
XSQLDA *in_sqlda;
 2SWLRQDOO\GHFODUHDYDULDEOHIRUDFFHVVLQJWKH;64/9$5VWUXFWXUHRIWKH
;64/'$
XSQLVAR *var;

'HFODULQJDSRLQWHUWRWKH;64/9$5VWUXFWXUHLVQRWQHFHVVDU\EXWFDQVLPSOLI\
UHIHUHQFLQJWKHVWUXFWXUHLQVXEVHTXHQWVWDWHPHQWV
 $OORFDWHPHPRU\IRUWKH;64/'$XVLQJWKH;64/'$B/(1*7+PDFUR7KH
IROORZLQJVWDWHPHQWDOORFDWHVVWRUDJHIRULQBVTOGD
in_sqlda = (XSQLDA *)malloc(XSQLDA_LENGTH(10));
,QWKLVVWDWHPHQWVSDFHIRU;64/9$5VWUXFWXUHVLVDOORFDWHGDOORZLQJWKH;64/'$WR
DFFRPPRGDWHXSWRSDUDPHWHUV
 6HWWKHYHUVLRQILHOGRIWKH;64/'$WR64/'$B9(56,21DQGVHWWKHVTOQILHOGWR
LQGLFDWHWKHQXPEHURI;64/9$5VWUXFWXUHVDOORFDWHG
in_sqlda_version = SQLDA_VERSION1;
in_sqlda->sqln = 10;

4 3UHSDULQJDQGH[HFXWLQJDVWDWHPHQWVWULQJZLWKSDUDPHWHUV
$IWHUDQ;64/'$LVFUHDWHGIRUKROGLQJDVWDWHPHQWVWULQJ·VSDUDPHWHUVWKHVWDWHPHQWVWULQJ
FDQEHFUHDWHGDQGSUHSDUHG/RFDOYDULDEOHVFRUUHVSRQGLQJWRWKHSODFHKROGHUSDUDPHWHUVLQ
WKHVWULQJPXVWEHDVVLJQHGWRWKHLUFRUUHVSRQGLQJVTOGDWDILHOGVLQWKH;64/9$5VWUXFWXUHV
7RSUHSDUHDQGH[HFXWHDQRQTXHU\VWDWHPHQWVWULQJZLWKSDUDPHWHUVIROORZWKHVHVWHSV
 (OLFLWDVWDWHPHQWVWULQJIURPWKHXVHURUFUHDWHRQHWKDWFRQWDLQVWKH64/
VWDWHPHQWWREHSURFHVVHG)RUH[DPSOHWKHIROORZLQJVWDWHPHQWFUHDWHVDQ64/
VWDWHPHQWVWULQJZLWKSODFHKROGHUSDUDPHWHUV
char *str = "UPDATE DEPARTMENT SET BUDGET = ?, LOCATION = ?";
7KLVVWDWHPHQWVWULQJFRQWDLQVWZRSDUDPHWHUVDYDOXHWREHDVVLJQHGWRWKH%8'*(7ILHOG
DQGDYDOXHWREHDVVLJQHGWRWKH/2&$7,21ILHOG
 3DUVHDQGQDPHWKHVWDWHPHQWVWULQJZLWK35(3$5(7KHQDPHLVXVHGLQ
VXEVHTXHQWFDOOVWR'(6&5,%(DQG(;(&87(

PROGRAMMER’S GUIDE 263


CHAPTER 14 USING DYNAMIC SQL

EXEC SQL
PREPARE SQL_STMT FROM :str;
64/B6707LVWKHQDPHDVVLJQHGWRWKHSUHSDUHGVWDWHPHQWVWULQJ
 8VH'(6&5,%(,1387WRILOOWKHLQSXW;64/'$ZLWKLQIRUPDWLRQDERXWWKH
SDUDPHWHUVFRQWDLQHGLQWKH64/VWDWHPHQW
EXEC SQL
DESCRIBE INPUT SQL_STMT USING SQL DESCRIPTOR in_sqlda;
 &RPSDUHWKHYDOXHRIWKHVTOQILHOGRIWKH;64/'$WRWKHYDOXHRIWKHVTOGILHOG
WRPDNHVXUHHQRXJK;64/9$5VDUHDOORFDWHGWRKROGLQIRUPDWLRQDERXWHDFK
SDUDPHWHUVTOQVKRXOGEHDWOHDVWDVODUJHDVVTOQ,IQRWIUHHWKHVWRUDJH
SUHYLRXVO\DOORFDWHGWRWKHLQSXWGHVFULSWRUUHDOORFDWHVWRUDJHWRUHIOHFWWKH
QXPEHURISDUDPHWHUVVSHFLILHGE\VTOGUHVHWVTOQDQGYHUVLRQWKHQH[HFXWH
'(6&5,%(,1387DJDLQ
if (in_sqlda->sqld > in_sqlda->sqln)
{
n = in_sqlda->sqld;
free(in_sqlda);
in_sqlda = (XSQLDA *)malloc(XSQLDA_LENGTH(n));
in_sqlda->sqln = n;
in_sqlda->version = SQLDA_VERSION1;
EXEC SQL
DESCRIBE INPUT SQL_STMT USING SQL DESCRIPTOR in_sqlda;
}

 3URFHVVHDFK;64/9$5SDUDPHWHUVWUXFWXUHLQWKH;64/'$3URFHVVLQJD
SDUDPHWHUVWUXFWXUHLQYROYHVXSWRIRXUVWHSV
 &RHUFLQJDSDUDPHWHU·VGDWDW\SH RSWLRQDO 
 $OORFDWLQJORFDOVWRUDJHIRUWKHGDWDSRLQWHGWRE\WKHVTOGDWDILHOGRIWKH;64/9$57KLV
VWHSLVRQO\UHTXLUHGLIVSDFHIRUORFDOYDULDEOHVLVQRWDOORFDWHGXQWLOUXQWLPH7KH
IROORZLQJH[DPSOHLOOXVWUDWHVG\QDPLFDOORFDWLRQRIORFDOYDULDEOHVWRUDJHVSDFH
 3URYLGLQJDYDOXHIRUWKHSDUDPHWHUFRQVLVWHQWZLWKLWVGDWDW\SH UHTXLUHG 
 3URYLGLQJD18//YDOXHLQGLFDWRUIRUWKHSDUDPHWHU
7KHIROORZLQJFRGHH[DPSOHLOOXVWUDWHVWKHVHVWHSVORRSLQJWKURXJKHDFK;64/9$5
VWUXFWXUHLQWKHLQBVTOGD;64/'$
for (i=0, var = in_sqlda->sqlvar; i < in_sqlda->sqld; i++, var++)
{
/* Process each XSQLVAR parameter structure here.
The parameter structure is pointed to by var.*/
dtype = (var->sqltype & ~1) /* drop NULL flag for now */

264 INTERBASE 5
DSQL PROGRAMMING METHODS

switch(dtype)
{
case SQL_VARYING: /* coerce to SQL_TEXT */
var->sqltype = SQL_TEXT;
/* Allocate local variable storage. */
var->sqldata = (char *)malloc(sizeof(char)*var->sqllen);
. . .
break;
case SQL_TEXT:
var->sqldata = (char *)malloc(sizeof(char)*var->sqllen);
/* Provide a value for the parameter. */
. . .
break;
case SQL_LONG:
var->sqldata = (char *)malloc(sizeof(long));
/* Provide a value for the parameter. */
*(long *)(var->sqldata) = 17;
break;
. . .
} /* End of switch statement. */
if (sqltype & 1)
{
/* Allocate variable to hold NULL status. */
var->sqlind = (short *)malloc(sizeof(short));
}
} /* End of for loop. */

)RUPRUHLQIRUPDWLRQDERXWGDWDW\SHFRHUFLRQDQG18//LQGLFDWRUVVHH´&RHUFLQJ
GDWDW\SHVµRQSDJH 
 ([HFXWHWKHQDPHGVWDWHPHQWVWULQJZLWK(;(&87(5HIHUHQFHWKHSDUDPHWHUV
LQWKHLQSXW;64/'$ZLWKWKH86,1*64/'(6&5,3725FODXVH)RUH[DPSOHWKH
IROORZLQJVWDWHPHQWH[HFXWHVDVWDWHPHQWVWULQJQDPHG64/B6707
EXEC SQL
EXECUTE SQL_STMT USING SQL DESCRIPTOR in_sqlda;

4 5HH[HFXWLQJWKHVWDWHPHQWVWULQJ
2QFHDQRQTXHU\VWDWHPHQWVWULQJZLWKSDUDPHWHUVLVSUHSDUHGLWFDQEHH[HFXWHGDVRIWHQ
DVUHTXLUHGLQDQDSSOLFDWLRQ%HIRUHHDFKVXEVHTXHQWH[HFXWLRQWKHLQSXW;64/'$FDQEH
VXSSOLHGZLWKQHZSDUDPHWHUDQG18//LQGLFDWRUGDWD
7RVXSSO\QHZSDUDPHWHUDQG18//LQGLFDWRUGDWDIRUDSUHSDUHGVWDWHPHQWUHSHDWVWHSV
²RI´3UHSDULQJDQG([HFXWLQJD6WDWHPHQW6WULQJZLWK3DUDPHWHUVµLQWKLVFKDSWHU

PROGRAMMER’S GUIDE 265


CHAPTER 14 USING DYNAMIC SQL

Method 3: Query statements without parameters


7KHUHDUHWKUHHVWHSVWRSURFHVVLQJDQ64/TXHU\VWDWHPHQWVWULQJZLWKRXWSDUDPHWHUV
 3UHSDULQJDQRXWSXW;64/'$WRSURFHVVWKHVHOHFWOLVWLWHPVUHWXUQHGZKHQWKH
TXHU\LVH[HFXWHG
 3UHSDULQJWKHVWDWHPHQWVWULQJ
 8VLQJDFXUVRUWRH[HFXWHWKHVWDWHPHQWDQGUHWULHYHVHOHFWOLVWLWHPVIURPWKH
RXWSXW;64/'$

4 3UHSDULQJWKHRXWSXW;64/'$
0RVWTXHULHVUHWXUQRQHRUPRUHURZVRIGDWDUHIHUUHGWRDVDVHOHFWOLVW%HFDXVHWKHQXPEHU
DQGNLQGRILWHPVUHWXUQHGDUHXQNQRZQZKHQDVWDWHPHQWVWULQJLVFUHDWHGDQRXWSXW
;64/'$PXVWEHFUHDWHGWRVWRUHVHOHFWOLVWLWHPVWKDWDUHUHWXUQHGDWUXQWLPH7RSUHSDUH
WKH;64/'$IROORZWKHVHVWHSV
 'HFODUHDYDULDEOHWRKROGWKH;64/'$QHHGHGWRVWRUHWKHFROXPQGDWDIRUHDFK
URZWKDWZLOOEHIHWFKHG)RUH[DPSOHWKHIROORZLQJGHFODUDWLRQFUHDWHVDQ
;64/'$FDOOHGRXWBVTOGD
XSQLDA *out_sqlda;

 2SWLRQDOO\GHFODUHDYDULDEOHIRUDFFHVVLQJWKH;64/9$5VWUXFWXUHRIWKH
;64/'$
XSQLVAR *var;

'HFODULQJDSRLQWHUWRWKH;64/9$5VWUXFWXUHLVQRWQHFHVVDU\EXWFDQVLPSOLI\
UHIHUHQFLQJWKHVWUXFWXUHLQVXEVHTXHQWVWDWHPHQWV
 $OORFDWHPHPRU\IRUWKH;64/'$XVLQJWKH;64/'$B/(1*7+PDFUR7KH
IROORZLQJVWDWHPHQWDOORFDWHVVWRUDJHIRURXWBVTOGD
out_sqlda = (XSQLDA *)malloc(XSQLDA_LENGTH(10));

6SDFHIRU;64/9$5VWUXFWXUHVLVDOORFDWHGLQWKLVVWDWHPHQWHQDEOLQJWKH;64/'$WR
DFFRPPRGDWHXSWRVHOHFWOLVWLWHPV
 6HWWKHYHUVLRQILHOGRIWKH;64/'$WR64/'$B9(56,21DQGVHWWKHVTOQILHOG
RIWKH;64/'$WRLQGLFDWHWKHQXPEHURI;64/9$5VWUXFWXUHVDOORFDWHG
out_sqlda->version = SQLDA_VERSION1;
out_sqlda->sqln = 10;

266 INTERBASE 5
DSQL PROGRAMMING METHODS

4 3UHSDULQJDTXHU\VWDWHPHQWVWULQJ
$IWHUDQ;64/'$LVFUHDWHGIRUKROGLQJWKHLWHPVUHWXUQHGE\DTXHU\VWDWHPHQWVWULQJWKH
VWDWHPHQWVWULQJFDQEHFUHDWHGSUHSDUHGDQGGHVFULEHG:KHQDVWDWHPHQWVWULQJLV
H[HFXWHG,QWHU%DVHFUHDWHVWKHVHOHFWOLVWRIVHOHFWHGURZV
7RSUHSDUHDTXHU\VWDWHPHQWVWULQJIROORZWKHVHVWHSV
 (OLFLWDVWDWHPHQWVWULQJIURPWKHXVHURUFUHDWHRQHWKDWFRQWDLQVWKH64/
VWDWHPHQWWREHSURFHVVHG)RUH[DPSOHWKHIROORZLQJVWDWHPHQWFUHDWHVDQ64/
VWDWHPHQWVWULQJWKDWSHUIRUPVDTXHU\
char *str = "SELECT * FROM CUSTOMER";

7KHVWDWHPHQWDSSHDUVWRKDYHRQO\RQHVHOHFWOLVWLWHP 7KHDVWHULVNLVDZLOGFDUG
V\PEROWKDWVWDQGVIRUDOORIWKHFROXPQVLQWKHWDEOHVRWKHDFWXDOQXPEHURILWHPV
UHWXUQHGHTXDOVWKHQXPEHURIFROXPQVLQWKHWDEOH
 3DUVHDQGQDPHWKHVWDWHPHQWVWULQJZLWK35(3$5(7KHQDPHLVXVHGLQ
VXEVHTXHQWFDOOVWRVWDWHPHQWVVXFKDV'(6&5,%(DQG(;(&87(
EXEC SQL
PREPARE SQL_STMT FROM :str;

64/B6707LVWKHQDPHDVVLJQHGWRWKHSUHSDUHGVWDWHPHQWVWULQJ
 8VH'(6&5,%(287387WRILOOWKHRXWSXW;64/'$ZLWKLQIRUPDWLRQDERXWWKH
VHOHFWOLVWLWHPVUHWXUQHGE\WKHVWDWHPHQW
EXEC SQL
DESCRIBE OUTPUT SQL_STMT INTO SQL DESCRIPTOR out_sqlda;

 &RPSDUHWKHVTOQILHOGRIWKH;64/'$WRWKHVTOGILHOGWRGHWHUPLQHLIWKHRXWSXW
GHVFULSWRUFDQDFFRPPRGDWHWKHQXPEHURIVHOHFWOLVWLWHPVVSHFLILHGLQWKH
VWDWHPHQW,IQRWIUHHWKHVWRUDJHSUHYLRXVO\DOORFDWHGWRWKHRXWSXWGHVFULSWRU
UHDOORFDWHVWRUDJHWRUHIOHFWWKHQXPEHURIVHOHFWOLVWLWHPVVSHFLILHGE\VTOGUHVHW
VTOQDQGYHUVLRQWKHQH[HFXWH'(6&5,%(287387DJDLQ
if (out_sqlda->sqld > out_sqlda->sqln)
{
n = out_sqlda->sqld;
free(out_sqlda);
out_sqlda = (XSQLDA *)malloc(XSQLDA_LENGTH(n));
out_sqlda->sqln = n;
out_sqlda->version = SQLDA_VERSION1;
EXEC SQL
DESCRIBE OUTPUT SQL_STMT INTO SQL DESCRIPTOR out_sqlda;
}

PROGRAMMER’S GUIDE 267


CHAPTER 14 USING DYNAMIC SQL

 6HWXSDQ;64/9$5VWUXFWXUHIRUHDFKLWHPUHWXUQHG6HWWLQJXSDQLWHP
VWUXFWXUHLQYROYHVWKHIROORZLQJVWHSV
 &RHUFLQJDQLWHP·VGDWDW\SH RSWLRQDO 
 $OORFDWLQJORFDOVWRUDJHIRUWKHGDWDSRLQWHGWRE\WKHVTOGDWDILHOGRIWKH;64/9$57KLV
VWHSLVRQO\UHTXLUHGLIVSDFHIRUORFDOYDULDEOHVLVQRWDOORFDWHGXQWLOUXQWLPH7KH
IROORZLQJH[DPSOHLOOXVWUDWHVG\QDPLFDOORFDWLRQRIORFDOYDULDEOHVWRUDJHVSDFH
 3URYLGLQJD18//YDOXHLQGLFDWRUIRUWKHSDUDPHWHU
7KHIROORZLQJFRGHH[DPSOHLOOXVWUDWHVWKHVHVWHSVORRSLQJWKURXJKHDFK;64/9$5
VWUXFWXUHLQWKHRXWBVTOGD;64/'$
for (i=0, var = out_sqlda->sqlvar; i < out_sqlda->sqld; i++, var++)
{
dtype = (var->sqltype & ~1) /* drop flag bit for now */
switch (dtype)
{
case SQL_VARYING:
var->sqltype = SQL_TEXT;
var->sqldata = (char *)malloc(sizeof(char)*var->sqllen + 2);
break;
case SQL_TEXT:
var->sqldata = (char *)malloc(sizeof(char)*var->sqllen);
break;
case SQL_LONG:
var->sqldata = (char *)malloc(sizeof(long));
break;
. . .
/* process remaining types */
} /* end of switch statements */
if (sqltype & 1)
{
/* allocate variable to hold NULL status */
var->sqlind = (short *)malloc(sizeof(short));
}
} /* end of for loop */

)RUPRUHLQIRUPDWLRQDERXWGDWDW\SHFRHUFLRQDQG18//LQGLFDWRUVVHH´&RHUFLQJ
GDWDW\SHVµRQSDJH 

268 INTERBASE 5
DSQL PROGRAMMING METHODS

4 ([HFXWLQJDVWDWHPHQWVWULQJZLWKLQWKHFRQWH[W RIDFXUVRU
7RUHWULHYHVHOHFWOLVWLWHPVIURPDSUHSDUHGVWDWHPHQWVWULQJWKHVWULQJPXVWEHH[HFXWHG
ZLWKLQWKHFRQWH[WRIDFXUVRU$OOFXUVRUGHFODUDWLRQVLQ,QWHU%DVHDUHIL[HGHPEHGGHG
VWDWHPHQWVLQVHUWHGLQWRWKHDSSOLFDWLRQEHIRUHLWLVFRPSLOHG'64/DSSOLFDWLRQGHYHORSHUV
PXVWDQWLFLSDWHWKHQHHGIRUFXUVRUVZKHQZULWLQJWKHDSSOLFDWLRQDQGGHFODUHWKHPDKHDGRI
WLPH
$ORRSLQJFRQVWUXFWLVXVHGWRIHWFKDVLQJOHURZDWDWLPHIURPWKHFXUVRUDQGWRSURFHVV
HDFKVHOHFWOLVWLWHP FROXPQ LQWKDWURZEHIRUHWKHQH[WURZLVIHWFKHG
7RH[HFXWHDVWDWHPHQWVWULQJZLWKLQWKHFRQWH[WRIDFXUVRUDQGUHWULHYHURZVRIVHOHFWOLVW
LWHPVIROORZWKHVHVWHSV
 'HFODUHDFXUVRUIRUWKHVWDWHPHQWVWULQJ)RUH[DPSOHWKHIROORZLQJVWDWHPHQW
GHFODUHVDFXUVRU'<1B&85625IRUWKH64/VWDWHPHQWVWULQJ64/B6707
EXEC SQL
DECLARE DYN_CURSOR CURSOR FOR SQL_STMT;

 2SHQWKHFXUVRU
EXEC SQL
OPEN DYN_CURSOR;

2SHQLQJWKHFXUVRUFDXVHVWKHVWDWHPHQWVWULQJWREHH[HFXWHGDQGDQDFWLYHVHWRIURZV
WREHUHWULHYHG)RUPRUHLQIRUPDWLRQDERXWFXUVRUVDQGDFWLYHVHWVVHH&KDSWHU
´:RUNLQJZLWK'DWDµ
 )HWFKRQHURZDWDWLPHDQGSURFHVVWKHVHOHFWOLVWLWHPV FROXPQV LWFRQWDLQV
)RUH[DPSOHWKHIROORZLQJORRSVUHWULHYHRQHURZDWDWLPHIURP
'<1B&85625DQGSURFHVVHDFKLWHPLQWKHUHWULHYHGURZZLWKDQ
DSSOLFDWLRQVSHFLILFIXQFWLRQ KHUHFDOOHGprocess_column() 
while (SQLCODE == 0)
{
EXEC SQL
FETCH DYN_CURSOR USING SQL DESCRIPTOR out_sqlda;
if (SQLCODE == 100)
break;
for (i = 0; i < out_sqlda->sqld; i++)
{
process_column(out_sqlda->sqlvar[i]);
}
}

7KHprocess_column()IXQFWLRQPHQWLRQHGLQWKLVH[DPSOHSURFHVVHVHDFKUHWXUQHG
VHOHFWOLVWLWHP7KHIROORZLQJVNHOHWRQFRGHLOOXVWUDWHVKRZVXFKDIXQFWLRQFDQEHVHWXS

PROGRAMMER’S GUIDE 269


CHAPTER 14 USING DYNAMIC SQL

void process_column(XSQLVAR *var)


{
/* test for NULL value */
if ((var->sqltype & 1) && (*(var->sqlind) = -1))
{
/* process the NULL value here */
}
else
{
/* process the data instead */
}
. . .
}

 :KHQDOOWKHURZVDUHIHWFKHGFORVHWKHFXUVRU
EXEC SQL
CLOSE DYN_CURSOR;

4 5HH[HFXWLQJDTXHU\VWDWHPHQWVWULQJ
2QFHDTXHU\VWDWHPHQWVWULQJZLWKRXWSDUDPHWHUVLVSUHSDUHGLWFDQEHH[HFXWHGDVRIWHQDV
UHTXLUHGLQDQDSSOLFDWLRQE\FORVLQJDQGUHRSHQLQJLWVFXUVRU
7RUHRSHQDFXUVRUDQGSURFHVVVHOHFWOLVWLWHPVUHSHDWVWHSV²RI´([HFXWLQJD6WDWHPHQW
6WULQJ:LWKLQWKH&RQWH[WRID&XUVRUµLQWKLVFKDSWHU

Method 4: Query statements with parameters


7KHUHDUHIRXUVWHSVWRSURFHVVLQJDQ64/TXHU\VWDWHPHQWVWULQJZLWKSODFHKROGHU
SDUDPHWHUV
 3UHSDULQJDQLQSXW;64/'$WRSURFHVVDVWDWHPHQWVWULQJ·VSDUDPHWHUV
 3UHSDULQJDQRXWSXW;64/'$WRSURFHVVWKHVHOHFWOLVWLWHPVUHWXUQHGZKHQWKH
TXHU\LVH[HFXWHG
 3UHSDULQJWKHVWDWHPHQWVWULQJDQGLWVSDUDPHWHUV
 8VLQJDFXUVRUWRH[HFXWHWKHVWDWHPHQWXVLQJLQSXWSDUDPHWHUYDOXHVIURPDQ
LQSXW;64/'$DQGWRUHWULHYHVHOHFWOLVWLWHPVIURPWKHRXWSXW;64/'$

270 INTERBASE 5
DSQL PROGRAMMING METHODS

4 3UHSDULQJWKHLQSXW;64/'$
3ODFHKROGHUSDUDPHWHUVDUHUHSODFHGZLWKDFWXDOGDWDEHIRUHDSUHSDUHG64/VWDWHPHQWVWULQJ
LVH[HFXWHG%HFDXVHWKRVHSDUDPHWHUVDUHXQNQRZQZKHQWKHVWDWHPHQWVWULQJLVFUHDWHGDQ
LQSXW;64/'$PXVWEHFUHDWHGWRVXSSO\SDUDPHWHUYDOXHVDWUXQWLPH7RSUHSDUHWKH
;64/'$IROORZWKHVHVWHSV
 'HFODUHDYDULDEOHWRKROGWKH;64/'$QHHGHGWRSURFHVVSDUDPHWHUV)RU
H[DPSOHWKHIROORZLQJGHFODUDWLRQFUHDWHVDQ;64/'$FDOOHGLQBVTOGD
XSQLDA *in_sqlda;

 2SWLRQDOO\GHFODUHDYDULDEOHIRUDFFHVVLQJWKH;64/9$5VWUXFWXUHRIWKH
;64/'$
XSQLVAR *var;

'HFODULQJDSRLQWHUWRWKH;64/9$5VWUXFWXUHLVQRWQHFHVVDU\EXWFDQVLPSOLI\
UHIHUHQFLQJWKHVWUXFWXUHLQVXEVHTXHQWVWDWHPHQWV
 $OORFDWHPHPRU\IRUWKH;64/'$XVLQJWKH;64/'$B/(1*7+PDFUR7KH
IROORZLQJVWDWHPHQWDOORFDWHVVWRUDJHIRULQBVOTGD
in_sqlda = (XSQLDA *)malloc(XSQLDA_LENGTH(10));

,QWKLVVWDWHPHQWVSDFHIRU;64/9$5VWUXFWXUHVLVDOORFDWHGDOORZLQJWKH;64/'$WR
DFFRPPRGDWHXSWRLQSXWSDUDPHWHUV2QFHVWUXFWXUHVDUHDOORFDWHGDVVLJQYDOXHVWR
WKHVTOGDWDILHOGLQHDFK;64/9$5
 6HWWKHYHUVLRQILHOGRIWKH;64/'$WR64/'$B9(56,21DQGVHWWKHVTOQILHOG
RIWKH;64/'$WRLQGLFDWHWKHQXPEHURI;64/9$5VWUXFWXUHVDOORFDWHG
in_sqlda->version = SQLDA_VERSION1;
in_sqlda->sqln = 10;

4 3UHSDULQJWKHRXWSXW;64/'$
%HFDXVHWKHQXPEHUDQGNLQGRILWHPVUHWXUQHGDUHXQNQRZQZKHQDVWDWHPHQWVWULQJLV
H[HFXWHGDQRXWSXW;64/'$PXVWEHFUHDWHGWRVWRUHVHOHFWOLVWLWHPVWKDWDUHUHWXUQHGDWUXQ
WLPH7RSUHSDUHWKH;64/'$IROORZWKHVHVWHSV
 'HFODUHDYDULDEOHWRKROGWKH;64/'$QHHGHGWRSURFHVVSDUDPHWHUV)RU
H[DPSOHWKHIROORZLQJGHFODUDWLRQFUHDWHVDQ;64/'$FDOOHGRXWBVTOGD
XSQLDA *out_sqlda;

 2SWLRQDOO\GHFODUHDYDULDEOHIRUDFFHVVLQJWKH;64/9$5VWUXFWXUHRIWKH
;64/'$
XSQLVAR *var;

PROGRAMMER’S GUIDE 271


CHAPTER 14 USING DYNAMIC SQL

'HFODULQJDSRLQWHUWRWKH;64/9$5VWUXFWXUHLVQRWQHFHVVDU\EXWFDQVLPSOLI\
UHIHUHQFLQJWKHVWUXFWXUHLQVXEVHTXHQWVWDWHPHQWV
 $OORFDWHPHPRU\IRUWKH;64/'$XVLQJWKH;64/'$B/(1*7+PDFUR7KH
IROORZLQJVWDWHPHQWDOORFDWHVVWRUDJHIRURXWBVTOGD
out_sqlda = (XSQLDA *)malloc(XSQLDA_LENGTH(10));

6SDFHIRU;64/9$5VWUXFWXUHVLVDOORFDWHGLQWKLVVWDWHPHQWHQDEOLQJWKH;64/'$WR
DFFRPPRGDWHXSWRVHOHFWOLVWLWHPV
 6HWWKHYHUVLRQILHOGRIWKH;64/'$WR64/'$B9(56,21DQGVHWWKHVTOQILHOG
RIWKH;64/'$WRLQGLFDWHWKHQXPEHURI;64/9$5VWUXFWXUHVDOORFDWHG
out_sqlda->version = SQLDA_VERSION1;
out_sqlda->sqln = 10;

4 3UHSDULQJDTXHU\VWDWHPHQWVWULQJZLWKSDUDPHWHUV
$IWHUDQLQSXWDQGDQRXWSXW;64/'$DUHFUHDWHGIRUKROGLQJDVWDWHPHQWVWULQJ·VSDUDPHWHUV
DQGWKHVHOHFWOLVWLWHPVUHWXUQHGZKHQWKHVWDWHPHQWLVH[HFXWHGWKHVWDWHPHQWVWULQJFDQEH
FUHDWHGDQGSUHSDUHG:KHQDVWDWHPHQWVWULQJLVSUHSDUHG,QWHU%DVHUHSODFHVWKH
SODFHKROGHUSDUDPHWHUVLQWKHVWULQJZLWKLQIRUPDWLRQDERXWWKHDFWXDOSDUDPHWHUVXVHG7KH
LQIRUPDWLRQDERXWWKHSDUDPHWHUVPXVWEHDVVLJQHGWRWKHLQSXW;64/'$ DQGSHUKDSV
DGMXVWHG EHIRUHWKHVWDWHPHQWFDQEHH[HFXWHG:KHQWKHVWDWHPHQWVWULQJLVH[HFXWHG
,QWHU%DVHVWRUHVVHOHFWOLVWLWHPVLQWKHRXWSXW;64/'$
7RSUHSDUHDTXHU\VWDWHPHQWVWULQJZLWKSDUDPHWHUVIROORZWKHVHVWHSV
 (OLFLWDVWDWHPHQWVWULQJIURPWKHXVHURUFUHDWHRQHWKDWFRQWDLQVWKH64/
VWDWHPHQWWREHSURFHVVHG)RUH[DPSOHWKHIROORZLQJVWDWHPHQWFUHDWHVDQ64/
VWDWHPHQWVWULQJZLWKSODFHKROGHUSDUDPHWHUV
char *str = "SELECT * FROM DEPARTMENT WHERE BUDGET = ?, LOCATION = ?";

7KLVVWDWHPHQWVWULQJFRQWDLQVWZRSDUDPHWHUVDYDOXHWREHDVVLJQHGWRWKH%8'*(7ILHOG
DQGDYDOXHWREHDVVLJQHGWRWKH/2&$7,21ILHOG
 3UHSDUHDQGQDPHWKHVWDWHPHQWVWULQJZLWK35(3$5(7KHQDPHLVXVHGLQ
VXEVHTXHQWFDOOVWR'(6&5,%(DQG(;(&87(
EXEC SQL
PREPARE SQL_STMT FROM :str;

64/B6707LVWKHQDPHDVVLJQHGWRWKHSUHSDUHGVWDWHPHQWVWULQJ
 8VH'(6&5,%(,1387WRILOOWKHLQSXW;64/'$ZLWKLQIRUPDWLRQDERXWWKH
SDUDPHWHUVFRQWDLQHGLQWKH64/VWDWHPHQW
EXEC SQL
DESCRIBE INPUT SQL_STMT USING SQL DESCRIPTOR in_sqlda;

272 INTERBASE 5
DSQL PROGRAMMING METHODS

 &RPSDUHWKHVTOQILHOGRIWKH;64/'$WRWKHVTOGILHOGWRGHWHUPLQHLIWKHLQSXW
GHVFULSWRUFDQDFFRPPRGDWHWKHQXPEHURISDUDPHWHUVFRQWDLQHGLQWKH
VWDWHPHQW,IQRWIUHHWKHVWRUDJHSUHYLRXVO\DOORFDWHGWRWKHLQSXWGHVFULSWRU
UHDOORFDWHVWRUDJHWRUHIOHFWWKHQXPEHURISDUDPHWHUVVSHFLILHGE\VTOGUHVHWVTOQ
DQGYHUVLRQWKHQH[HFXWH'(6&5,%(,1387DJDLQ
if (in_sqlda->sqld > in_sqlda->sqln)
{
n = in_sqlda->sqld;
free(in_sqlda);
in_sqlda = (XSQLDA *)malloc(XSQLDA_LENGTH(n));
in_sqlda->sqln = n;
in_sqlda->version = SQLDA_VERSION1;
EXEC SQL
DESCRIBE INPUT SQL_STMT USING SQL DESCRIPTOR in_sqlda;
}

 3URFHVVHDFK;64/9$5SDUDPHWHUVWUXFWXUHLQWKHLQSXW;64/'$3URFHVVLQJD
SDUDPHWHUVWUXFWXUHLQYROYHVXSWRIRXUVWHSV
 &RHUFLQJDSDUDPHWHU·VGDWDW\SH RSWLRQDO 
 $OORFDWLQJORFDOVWRUDJHIRUWKHGDWDSRLQWHGWRE\WKHVTOGDWDILHOGRIWKH;64/9$57KLV
VWHSLVRQO\UHTXLUHGLIVSDFHIRUORFDOYDULDEOHVLVQRWDOORFDWHGXQWLOUXQWLPH7KH
IROORZLQJH[DPSOHLOOXVWUDWHVG\QDPLFDOORFDWLRQRIORFDOYDULDEOHVWRUDJHVSDFH
 3URYLGLQJDYDOXHIRUWKHSDUDPHWHUFRQVLVWHQWZLWKLWVGDWDW\SH UHTXLUHG 
 3URYLGLQJD18//YDOXHLQGLFDWRUIRUWKHSDUDPHWHU
7KHVHVWHSVPXVWEHIROORZHGLQWKHRUGHUSUHVHQWHG7KHIROORZLQJFRGHH[DPSOH
LOOXVWUDWHVWKHVHVWHSVORRSLQJWKURXJKHDFK;64/9$5VWUXFWXUHLQWKHLQBVTOGD;64/'$
for (i=0, var = in_sqlda->sqlvar; i < in_sqlda->sqld; i++, var++)
{
/* Process each XSQLVAR parameter structure here.
The parameter structure is pointed to by var.*/
dtype = (var->sqltype & ~1) /* drop flag bit for now */
switch (dtype)
{
case SQL_VARYING: /* coerce to SQL_TEXT */
var->sqltype = SQL_TEXT;
/* allocate proper storage */
var->sqldata = (char *)malloc(sizeof(char)*var->sqllen);
/* provide a value for the parameter. See case SQL_LONG */
. . .
break;

PROGRAMMER’S GUIDE 273


CHAPTER 14 USING DYNAMIC SQL

case SQL_TEXT:
var->sqldata = (char *)malloc(sizeof(char)*var->sqllen);
/* provide a value for the parameter. See case SQL_LONG */
. . .
break;
case SQL_LONG:
var->sqldata = (char *)malloc(sizeof(long));
/* provide a value for the parameter */
*(long *)(var->sqldata) = 17;
break;
. . .
} /* end of switch statement */
if (sqltype & 1)
{
/* allocate variable to hold NULL status */
var->sqlind = (short *)malloc(sizeof(short));
}
} /* end of for loop */

)RUPRUHLQIRUPDWLRQDERXWGDWDW\SHFRHUFLRQDQG18//LQGLFDWRUVVHH´&RHUFLQJ
GDWDW\SHVµRQSDJH 
 8VH'(6&5,%(287387WRILOOWKHRXWSXW;64/'$ZLWKLQIRUPDWLRQDERXWWKH
VHOHFWOLVWLWHPVUHWXUQHGE\WKHVWDWHPHQW
EXEC SQL
DESCRIBE OUTPUT SQL_STMT INTO SQL DESCRIPTOR out_sqlda;

 &RPSDUHWKHVTOQILHOGRIWKH;64/'$WRWKHVTOGILHOGWRGHWHUPLQHLIWKHRXWSXW
GHVFULSWRUFDQDFFRPPRGDWHWKHQXPEHURIVHOHFWOLVWLWHPVVSHFLILHGLQWKH
VWDWHPHQW,IQRWIUHHWKHVWRUDJHSUHYLRXVO\DOORFDWHGWRWKHRXWSXWGHVFULSWRU
UHDOORFDWHVWRUDJHWRUHIOHFWWKHQXPEHURIVHOHFWOLVWLWHPVVSHFLILHGE\VTOGUHVHW
VTOQDQGYHUVLRQDQGH[HFXWH'(6&5,%(287387DJDLQ
if (out_sqlda->sqld > out_sqlda->sqln)
{
n = out_sqlda->sqld;
free(out_sqlda);
out_sqlda = (XSQLDA *)malloc(XSQLDA_LENGTH(n));
out_sqlda->sqln = n;
out_sqlda->version = SQLDA_VERSION1;
EXEC SQL
DESCRIBE OUTPUT SQL_STMT INTO SQL DESCRIPTOR out_sqlda;
}
 6HWXSDQ;64/9$5VWUXFWXUHIRUHDFKLWHPUHWXUQHG6HWWLQJXSDQLWHP
VWUXFWXUHLQYROYHVWKHIROORZLQJVWHSV

274 INTERBASE 5
DSQL PROGRAMMING METHODS

 &RHUFLQJDQLWHP·VGDWDW\SH RSWLRQDO 
 $OORFDWLQJORFDOVWRUDJHIRUWKHGDWDSRLQWHGWRE\WKHVTOGDWDILHOGRIWKH;64/9$57KLV
VWHSLVRQO\UHTXLUHGLIVSDFHIRUORFDOYDULDEOHVLVQRWDOORFDWHGXQWLOUXQWLPH7KH
IROORZLQJH[DPSOHLOOXVWUDWHVG\QDPLFDOORFDWLRQRIORFDOYDULDEOHVWRUDJHVSDFH
 3URYLGLQJD18//YDOXHLQGLFDWRUIRUWKHSDUDPHWHU RSWLRQDO 
7KHIROORZLQJFRGHH[DPSOHLOOXVWUDWHVWKHVHVWHSVORRSLQJWKURXJKHDFK;64/9$5
VWUXFWXUHLQWKHRXWBVTOGD;64/'$
for (i=0, var = out_sqlda->sqlvar; i < out_sqlda->sqld; i++, var++)
{
dtype = (var->sqltype & ~1) /* drop flag bit for now */
switch (dtype)
{
case SQL_VARYING:
var->sqltype = SQL_TEXT;
break;
case SQL_TEXT:
var->sqldata = (char *)malloc(sizeof(char)*var->sqllen);
break;
case SQL_LONG:
var->sqldata = (char *)malloc(sizeof(long));
break;
/* process remaining types */
} /* end of switch statements */
if (sqltype & 1)
{
/* allocate variable to hold NULL status */
var->sqlind = (short *)malloc(sizeof(short));
}
} /* end of for loop */

)RUPRUHLQIRUPDWLRQDERXWGDWDW\SHFRHUFLRQDQG18//LQGLFDWRUVVHH´&RHUFLQJ
GDWDW\SHVµRQSDJH 

4 ([HFXWLQJDTXHU\VWDWHPHQWVWULQJZLWKLQWKHFRQWH[WRIDFXUVRU
7RUHWULHYHVHOHFWOLVWLWHPVIURPDVWDWHPHQWVWULQJWKHVWULQJPXVWEHH[HFXWHGZLWKLQWKH
FRQWH[WRIDFXUVRU$OOFXUVRUGHFODUDWLRQVLQ,QWHU%DVHDUHIL[HGHPEHGGHGVWDWHPHQWV
LQVHUWHGLQWRWKHDSSOLFDWLRQEHIRUHLWLVFRPSLOHG'64/DSSOLFDWLRQGHYHORSHUVPXVW
DQWLFLSDWHWKHQHHGIRUFXUVRUVZKHQZULWLQJWKHDSSOLFDWLRQDQGGHFODUHWKHPDKHDGRIWLPH
$ORRSLQJFRQVWUXFWLVXVHGWRIHWFKDVLQJOHURZDWDWLPHIURPWKHFXUVRUDQGWRSURFHVV
HDFKVHOHFWOLVWLWHP FROXPQ LQWKDWURZEHIRUHWKHQH[WURZLVIHWFKHG

PROGRAMMER’S GUIDE 275


CHAPTER 14 USING DYNAMIC SQL

7RH[HFXWHDVWDWHPHQWVWULQJZLWKLQWKHFRQWH[WRIDFXUVRUDQGUHWULHYHURZVRIVHOHFWOLVW
LWHPVIROORZWKHVHVWHSV
 'HFODUHDFXUVRUIRUWKHVWDWHPHQWVWULQJ)RUH[DPSOHWKHIROORZLQJVWDWHPHQW
GHFODUHVDFXUVRU'<1B&85625IRUWKHSUHSDUHG64/VWDWHPHQWVWULQJ
64/B6707
EXEC SQL
DECLARE DYN_CURSOR CURSOR FOR SQL_STMT;

 2SHQWKHFXUVRUVSHFLI\LQJWKHLQSXWGHVFULSWRU
EXEC SQL
OPEN DYN_CURSOR USING SQL DESCRIPTOR in_sqlda;

2SHQLQJWKHFXUVRUFDXVHVWKHVWDWHPHQWVWULQJWREHH[HFXWHGDQGDQDFWLYHVHWRIURZV
WREHUHWULHYHG)RUPRUHLQIRUPDWLRQDERXWFXUVRUVDQGDFWLYHVHWVVHH&KDSWHU
´:RUNLQJZLWK'DWDµ
 )HWFKRQHURZDWDWLPHDQGSURFHVVWKHVHOHFWOLVWLWHPV FROXPQV LWFRQWDLQV
)RUH[DPSOHWKHIROORZLQJORRSVUHWULHYHRQHURZDWDWLPHIURP'<1B&85625
DQGSURFHVVHDFKLWHPLQWKHUHWULHYHGURZZLWKDQDSSOLFDWLRQVSHFLILFIXQFWLRQ
KHUHFDOOHGprocess_column() 
while (SQLCODE == 0)
{
EXEC SQL
FETCH DYN_CURSOR USING SQL DESCRIPTOR out_sqlda;
if (SQLCODE == 100)
break;
for (i = 0; i < out_sqlda->sqld; i++)
{
process_column(out_sqlda->sqlvar[i]);
}
}

 :KHQDOOWKHURZVDUHIHWFKHGFORVHWKHFXUVRU
EXEC SQL
CLOSE DYN_CURSOR;

4 5HH[HFXWLQJDTXHU\VWDWHPHQWVWULQJZLWKSDUDPHWHUV
2QFHDTXHU\VWDWHPHQWVWULQJZLWKSDUDPHWHUVLVSUHSDUHGLWFDQEHXVHGDVRIWHQDVUHTXLUHG
LQDQDSSOLFDWLRQ%HIRUHHDFKVXEVHTXHQWXVHWKHLQSXW;64/'$FDQEHVXSSOLHGZLWKQHZ
SDUDPHWHUDQG18//LQGLFDWRUGDWD7KHFXUVRUPXVWEHFORVHGDQGUHRSHQHGEHIRUH
SURFHVVLQJFDQRFFXU

276 INTERBASE 5
DSQL PROGRAMMING METHODS

7RSURYLGHQHZSDUDPHWHUVWRWKHLQSXW;64/'$IROORZVWHSV²RI´3UHSDULQJD4XHU\
6WDWHPHQW6WULQJZLWK3DUDPHWHUVµLQWKLVFKDSWHU
7RSURYLGHQHZLQIRUPDWLRQWRWKHRXWSXW;64/'$IROORZVWHSV²RI´3UHSDULQJD4XHU\
6WDWHPHQW6WULQJZLWK3DUDPHWHUVµLQWKLVFKDSWHU
7RUHRSHQDFXUVRUDQGSURFHVVVHOHFWOLVWLWHPVUHSHDWVWHSV²RI´([HFXWLQJD4XHU\
6WDWHPHQW6WULQJ:LWKLQWKH&RQWH[WRID&XUVRUµLQWKLVFKDSWHU

PROGRAMMER’S GUIDE 277


CHAPTER

Preprocessing, Compiling,
Chapter15
15
and Linking

7KLVFKDSWHUGHVFULEHVKRZWRSUHSURFHVVDSURJUDPE\XVLQJgpreDQGKRZWRFRPSLOHDQG
OLQNLWIRUH[HFXWLRQ

Preprocessing
$IWHUFRGLQJDQ64/RUG\QDPLF64/ '64/ SURJUDPWKHSURJUDPPXVWEHSUHSURFHVVHG
ZLWKgpreEHIRUHLWFDQEHFRPSLOHGgpreWUDQVODWHV64/DQG'64/FRPPDQGVLQWR
VWDWHPHQWVWKHKRVWODQJXDJHFRPSLOHUDFFHSWVE\JHQHUDWLQJ,QWHU%DVHOLEUDU\IXQFWLRQFDOOV
gpreWUDQVODWHV64/DQG'64/GDWDEDVHYDULDEOHVLQWRRQHVWKHKRVWODQJXDJHFRPSLOHU
DFFHSWVDQGGHFODUHVWKHVHYDULDEOHVLQKRVWODQJXDJHIRUPDWgpreDOVRGHFODUHVFHUWDLQ
YDULDEOHVDQGGDWDVWUXFWXUHVUHTXLUHGE\64/VXFKDVWKH64/&2'(YDULDEOHDQGWKH
H[WHQGHG64/GHVFULSWRUDUHD ;64/'$ XVHGE\'64/

Using gpre
7KHV\QWD[IRUgpreLV
gpre [-language] [-options] infile [outfile]

279
CHAPTER 15 PREPROCESSING, COMPILING, AND LINKING

7KHLQILOHDUJXPHQWVSHFLILHVWKHQDPHRIWKHLQSXWILOH
7KHRSWLRQDORXWILOHDUJXPHQWVSHFLILHVWKHQDPHRIWKHRXWSXWILOH,IQRILOHLVVSHFLILHGgpre
VHQGVLWVRXWSXWWRDILOHZLWKWKHVDPHQDPHDVWKHLQSXWILOHZLWKDQH[WHQVLRQGHSHQGLQJ
RQWKHODQJXDJHRIWKHLQSXWILOH
gpreKDVVZLWFKHVWKDWDOORZ\RXWRVSHFLI\WKHODQJXDJHRIWKHVRXUFHSURJUDPDQGDQXPEHU
RIRWKHURSWLRQV<RXFDQSODFHWKHVZLWFKHVHLWKHUEHIRUHRUDIWHUWKHLQSXWDQGRXWSXWILOH
VSHFLILFDWLRQ(DFKVZLWFKPXVWLQFOXGHDWOHDVWDK\SKHQSUHFHGHGE\DVSDFHDQGDXQLTXH
FKDUDFWHUVSHFLI\LQJWKHVZLWFK

4 /DQJXDJHVZLWFKHV
7KHODQJXDJHVZLWFKVSHFLILHVWKHODQJXDJHRIWKHVRXUFHSURJUDP&DQG&DUHODQJXDJHV
DYDLODEOHRQDOOSODWIRUPV7KHVZLWFKHVDUHVKRZQLQWKHIROORZLQJWDEOH

Switch Language
-c C
-cxx C++
TABLE 15.1 gpre language switches available on all platforms

,QDGGLWLRQVRPHSODWIRUPVVXSSRUWRWKHUODQJXDJHVLIDQDGGLWLRQDO,QWHU%DVHOLFHQVHIRUWKH
ODQJXDJHLVSXUFKDVHG7KHIROORZLQJWDEOHOLVWVWKHDYDLODEOHODQJXDJHVDQGWKHFRUUHVSRQGLQJ
VZLWFKHV

Switch Language
-al[sys] Ada (Alsys)
-a[da] Ada (VERDIX, VMS, Telesoft)
-ansi ANSI-85 COBOL
-co[bol] COBOL
-f[ortran] FORTRAN
-pa[scal] Pascal
TABLE 15.2 Additional gpre language switches

)RUH[DPSOHWRSUHSURFHVVD&SURJUDPFDOOHGFHQVXVHW\SH
gpre -c census.e

280 INTERBASE 5
PREPROCESSING

4 2SWLRQVZLWFKHV
7KHRSWLRQVZLWFKHVVSHFLI\SUHSURFHVVLQJRSWLRQV7KHIROORZLQJWDEOHGHVFULEHVWKH
DYDLODEOHVZLWFKHV

Switch Description
-charset name Determines the active character set at compile time, where name is the
character set name.
-d[atabase] filename Declares a database for programs. filename is the file name of the database to
access. Use this option if a program contains SQL statements and does not
attach to the database itself. Do not use this option if the program includes a
database declaration.
-d_float VAX/VMS only. Specifies that double-precision data will be passed from the
application in D_FLOAT format and stored in the database in G_FLOAT format.
Data comparisons within the database will be performed in G_FLOAT format.
Data returned to the application from the database will be in D_FLOAT format.
-e[ither_case] Enables gpre to recognize both uppercase and lowercase. Use the
-either_case switch whenever SQL keywords appear in code in lowercase
letters. If case is mixed, and this switch is not used, gpre cannot process the
input file. This switch is not
necessary with languages other than C, since they are case-insensitive.
-m[anual] Suppresses the automatic generation of transactions. Use the
-m switch for SQL programs that perform their own transaction handling, and
for all DSQL programs that must, by definition, explicitly control their own
transactions.
-n[o_lines] Suppresses line numbers for C programs.
-o[utput] Directs gpre’s output to standard output, rather than to a file.
-password password Specifies password, the database password, if the program connects to a
database that requires one.
TABLE 15.3 gpre option switches

PROGRAMMER’S GUIDE 281


CHAPTER 15 PREPROCESSING, COMPILING, AND LINKING

Switch Description
-r[aw] Prints BLR as raw numbers, rather than as their mnemonic equivalents. This
option cam be useful for making the gpre output file smaller; however, it will
be unreadable.
-sqlda [old | new] Argument old specifies SQLDA, new specifies XSQLDA. If this switch is not used,
the default is XSQLDA.
-user username Specifies username, the database user name, if the program connects to a
database that requires one.
-x handle Gives the database handle identified with the -database option an external
declaration. This option directs the program to pick up a global declaration
from another linked module. Use only if the -d switch is also used.
-z Print the version number of gpre and the version number of all declared
databases. These databases can be declared either in the program or with the
-database switch.
TABLE 15.3 gpre option switches (continued)

)RUVLWHVZLWKWKHDSSURSULDWHOLFHQVHDQGDUHXVLQJDODQJXDJHRWKHUWKDQ&DGGLWLRQDOgpre
RSWLRQVFDQEHVSHFLILHGDVGHVFULEHGLQWKHIROORZLQJWDEOH

Switch Description
-h[andles] pkg Specifies, pkg, an Ada handles package.
TABLE 15.4 Language-specific gpre option switches

4 ([DPSOHV
7KHIROORZLQJFRPPDQGSUHSURFHVVHVD&SURJUDPLQDILOHQDPHGDSSOH7KHRXWSXWILOH
ZLOOEHDSSOF6LQFHQRGDWDEDVHLVVSHFLILHGWKHVRXUFHFRGHPXVWFRQQHFWWRWKHGDWDEDVH
gpre -c appl1

7KHIROORZLQJFRPPDQGLVWKHVDPHDVWKHSUHYLRXVH[FHSWWKDWLWGRHVQRWDVVXPHWKH
VRXUFHFRGHRSHQVDGDWDEDVHLQVWHDGH[SOLFLWO\GHFODULQJWKHGDWDEDVHP\GEJGE
gpre -c appl1 -d mydb.gdb

282 INTERBASE 5
PREPROCESSING

Using a file extension to specify language


,QDGGLWLRQWRXVLQJDODQJXDJHVZLWFKWRVSHFLI\WKHKRVWODQJXDJHLWLVDOVRSRVVLEOHWR
LQGLFDWHWKHKRVWODQJXDJHZLWKWKHILOHQDPHH[WHQVLRQRIWKHVRXUFHILOH7KHIROORZLQJWDEOH
OLVWVWKHILOHQDPHH[WHQVLRQVIRUHDFKODQJXDJHWKDWgpreVXSSRUWVDQGWKHGHIDXOWH[WHQVLRQ
RIWKHRXWSXWILOH

Language Input file extension Default output file extension


Ada (VERDIX) ea a
Ada (Alsys, Telesoft) eada ada
C e c
C++ exx cxx
COBOL ecob cob
FORTRAN ef f
Pascal epas pas
TABLE 15.5 File extensions for language specification

)RUH[DPSOHWRSUHSURFHVVD&2%2/SURJUDPFDOOHGFHQVXVHFREW\SH
gpre census_report.ecob

7KLVJHQHUDWHVDQRXWSXWILOHFDOOHGFHQVXVFRE
:KHQVSHFLI\LQJDILOHQDPHH[WHQVLRQLWLVSRVVLEOHWRVSHFLI\DODQJXDJHVZLWFKDVZHOO
gpre -cob census.ecob

Specifying the source file


%HFDXVHERWKWKHODQJXDJHVZLWFKDQGWKHILOHQDPHH[WHQVLRQDUHRSWLRQDOgpre FDQ
HQFRXQWHUWKUHHGLIIHUHQWVLWXDWLRQV
g $ODQJXDJHVZLWFKDQGLQSXWILOHZLWKQRH[WHQVLRQ
g 1RODQJXDJHVZLWFKEXWDQLQSXWILOHZLWKH[WHQVLRQ
g 1HLWKHUDODQJXDJHVZLWFKQRUDILOHH[WHQVLRQ
7KLVVHFWLRQGHVFULEHVgpre·VEHKDYLRULQHDFKRIWKHVHFDVHV

PROGRAMMER’S GUIDE 283


CHAPTER 15 PREPROCESSING, COMPILING, AND LINKING

Language switch and no input file extension


,IgpreHQFRXQWHUVDODQJXDJHVZLWFKEXWWKHVSHFLILHGLQSXWILOHKDVQRH[WHQVLRQ, LWGRHV
WKHIROORZLQJ
 ,WORRNVIRUWKHLQSXWILOHZLWKRXWDQH[WHQVLRQ,Igpre ILQGVWKHILOHLWSURFHVVHV
LWDQGJHQHUDWHVDQRXWSXWILOHZLWKWKHDSSURSULDWHH[WHQVLRQ
,Igpre GRHVQRWILQGWKHLQSXWILOHLWORRNVIRUWKHILOHZLWKWKHH[WHQVLRQWKDW
FRUUHVSRQGVWRWKHLQGLFDWHGODQJXDJH ,ILWILQGVVXFKDILOHLWJHQHUDWHVDQRXWSXWILOH
ZLWKWKHDSSURSULDWHH[WHQVLRQ
 ,Igpre FDQQRWILQGHLWKHUWKHQDPHGILOHRUWKHQDPHGILOHZLWKWKHDSSURSULDWH
H[WHQVLRQLWUHWXUQVWKHIROORZLQJHUURU
gpre: can’t open filename or filename.extension

ILOHQDPHLVWKHILOHVSHFLILHGLQWKHgpre FRPPDQGH[WHQVLRQLVWKHODQJXDJHVSHFLILFILOH
H[WHQVLRQIRUWKHVSHFLILHGSURJUDP
)RUH[DPSOHVXSSRVHWKHIROORZLQJFRPPDQGLVLVVXHG
gpre -c census

gpreSHUIRUPVWKHIROORZLQJVHTXHQFHRIDFWLRQV
 ,WORRNVIRUDILOHFDOOHGFHQVXVZLWKRXWDQH[WHQVLRQ,ILWILQGVWKHILOHLWSURFHVVHV
LWDQGJHQHUDWHVFHQVXVF
 ,ILWFDQQRWILQGFHQVXVLWORRNVIRUDILOHFDOOHGFHQVXVH,I LWILQGVFHQVXVHLW
SURFHVVHVWKHILOHDQGJHQHUDWHVFHQVXVF
 ,Iit FDQQRWILQGFHQVXVRUFHQVXVHLWUHWXUQVWKLVHUURU
gpre: can’t open census or census.e

No language switch and an input file with extension


,IDODQJXDJHVZLWFKLVQRWVSHFLILHGEXWWKHLQSXWILOHLQFOXGHVDILOHQDPHH[WHQVLRQgpre
ORRNVIRUWKHVSHFLILHGILOHDQGDVVXPHVWKHODQJXDJHLVLQGLFDWHGE\WKHH[WHQVLRQ
)RUH[DPSOHVXSSRVHWKHIROORZLQJFRPPDQGLVSURFHVVHG
gpre census.e

gpre ORRNVIRUDILOHFDOOHGFHQVXVH,IgpreILQGVWKLVILOHLWSURFHVVHVLWDVD&SURJUDPDQG
JHQHUDWHVDQRXWSXWILOHFDOOHGFHQVXVF,IgpreGRHVQRWILQGWKLVILOHLWUHWXUQVWKHIROORZLQJ
HUURU
gpre: can’t open census.e

284 INTERBASE 5
COMPILING AND LINKING

Neither a language switch nor a file extension


,Igpre ILQGV QHLWKHUDODQJXDJHH[WHQVLRQQRUDILOHQDPHH[WHQVLRQLWORRNVIRUDILOHLQWKH
IROORZLQJRUGHU
 ILOHQDPHH &
 ILOHQDPHHSDV 3DVFDO
 ILOHQDPHHI )2575$1
 ILOHQDPHHFRE &2%2/
 ILOHQDPHHD 9(5',;$GD
 ILOHQDPHHDGD $OV\VDQG7HOHVRIW$GD
,IgpreILQGVVXFKDILOHLWJHQHUDWHVDQRXWSXWILOHZLWKWKHDSSURSULDWHH[WHQVLRQ,Igpre
GRHVQRWILQGWKHILOHLWUHWXUQVWKHIROORZLQJHUURU
gpre: can’t find filename with any known extension. Giving up.

Compiling and linking


$IWHUSUHSURFHVVLQJDSURJUDPLWPXVWEHFRPSLOHGDQGOLQNHG&RPSLOLQJFUHDWHVDQREMHFW
PRGXOHIURPWKHSUHSURFHVVHGVRXUFHILOH8VHDKRVWODQJXDJHFRPSLOHUWRFRPSLOHWKH
SURJUDP
7KHOLQNLQJSURFHVVUHVROYHVH[WHUQDOUHIHUHQFHVDQGFUHDWHVDQH[HFXWDEOHREMHFW8VHWKH
WRROVDYDLODEOHRQDJLYHQSODWIRUPWROLQNDSURJUDP·VREMHFWPRGXOHWRRWKHUREMHFWPRGXOHV
DQGOLEUDULHVEDVHGRQWKHSODWIRUPRSHUDWLQJV\VWHPDQGKRVWODQJXDJHXVHG

Compiling an Ada program


%HIRUHFRPSLOLQJDQ$GDSURJUDPEHVXUHWKH$GDOLEUDU\FRQWDLQVWKHSDFNDJHLQWHUEDVHDGD
RULQWHUEDVHDIRU9(5',;$GD 7KLVSDFNDJHLVLQWKH,QWHU%DVHLQFOXGHGLUHFWRU\
7RXVHWKHSURJUDPVLQWKH,QWHU%DVHH[DPSOHVGLUHFWRU\XVHWKHSDFNDJHEDVLFBLRDGD RU
EDVLFBLRDIRU9(5',;$GD DOVRORFDWHGLQWKHH[DPSOHVGLUHFWRU\

Linking
2Q8QL[SODWIRUPVSURJUDPVFDQEHOLQNHGWRWKHIROORZLQJOLEUDULHV

PROGRAMMER’S GUIDE 285


CHAPTER 15 PREPROCESSING, COMPILING, AND LINKING

g $OLEUDU\WKDWXVHVSLSHVREWDLQHGZLWKWKHOJGVRSWLRQ7KLVOLEUDU\\LHOGVIDVWHUOLQNVDQG
VPDOOHULPDJHV,WDOVROHWV\RXUDSSOLFDWLRQZRUNZLWKQHZYHUVLRQVRI,QWHU%DVH
DXWRPDWLFDOO\ZKHQWKH\DUHLQVWDOOHG
g $OLEUDU\WKDWGRHVQRWXVHSLSHVREWDLQHGZLWKWKHOJGVBERSWLRQ7KLVOLEUDU\KDVIDVWHU
H[HFXWLRQEXWELQGVDQDSSOLFDWLRQWRDVSHFLILFYHUVLRQRI,QWHU%DVH:KHQLQVWDOOLQJDQHZ
YHUVLRQRI,QWHU%DVHSURJUDPVPXVWEHUHOLQNHGWRXVHWKHQHZIHDWXUHVRUGDWDEDVHVFUHDWHG
ZLWKWKDWYHUVLRQ
8QGHU6XQ26SURJUDPVFDQEHOLQNHGWRDVKDUHDEOHOLEUDU\E\XVLQJWKH
OJGVOLERSWLRQ7KLVFUHDWHVDG\QDPLFOLQNDWUXQWLPHDQG\LHOGVVPDOOHULPDJHVZLWKWKH
H[HFXWLRQVSHHGRIWKHIXOOOLEUDU\7KLVRSWLRQDOVRSURYLGHVWKHDELOLW\WRXSJUDGH,QWHU%DVH
YHUVLRQVDXWRPDWLFDOO\
)RUVSHFLILFLQIRUPDWLRQDERXWOLQNLQJRSWLRQVIRU,QWHU%DVHRQDSDUWLFXODUSODWIRUPFRQVXOW
WKHRQOLQHUHDGPHLQWKHLQWHUEDVHGLUHFWRU\

286 INTERBASE 5
APPENDIX

InterBase Document
AppendixA
A
Conventions

7KLVDSSHQGL[GHVFULEHVWKH,QWHU%DVHGRFXPHQWDWLRQVHWWKHSULQWLQJFRQYHQWLRQVXVHG
WRGLVSOD\LQIRUPDWLRQLQWH[WDQGLQFRGHH[DPSOHVDQGFRQYHQWLRQVIRUQDPLQJGDWDEDVH
REMHFWVDQGILOHVLQDSSOLFDWLRQV

287
APPENDIX A INTERBASE DOCUMENT CONVENTIONS

The InterBase documentation set


7KH,QWHU%DVHGRFXPHQWDWLRQVHWLVDQLQWHJUDWHGSDFNDJHGHVLJQHGIRUDOOOHYHOVRIXVHUV,W
FRQVLVWVRIILYHSULQWHGERRNV(DFKRIWKHVHERRNVLVDOVRSURYLGHGLQ$GREH$FUREDW3')
IRUPDWDQGLVDFFHVVLEOHRQOLQHWKURXJKWKH+HOSPHQX,I$GREH$FUREDWLVQRWDOUHDG\
LQVWDOOHGRQ\RXUV\VWHP\RXFDQILQGLWRQWKH,QWHU%DVHGLVWULEXWLRQ&'520RUDW
KWWSZZZDGREHFRPSURGLQGH[DFUREDWUHDGVWHSKWPO$FUREDWLVDYDLODEOHIRU:LQGRZV17
:LQGRZVDQGPRVWIODYRUVRI81,;:LQGRZVXVHUVDOVRKDYHKHOSDYDLODEOHWKURXJKWKH
:LQ+HOSV\VWHP

Book Description
Operations Guide Provides an introduction to InterBase and an explanation of tools and
procedures for performing administrative tasks on databases and database
servers. Also includes full reference on InterBase utilities, including isql, gbak,
Server Manager for Windows, and others.
Data Definition Guide Explains how to create, alter, and delete database objects through ISQL.
Language Reference Describes SQL and DSQL syntax and usage.
Programmer’s Guide Describes how to write embedded SQL and DSQL database applications in a
host language, precompiled through gpre.
API Guide Explains how to write database applications using the InterBase API.
TABLE A.1 Books in the InterBase 5.0 documentation set

288 INTERBASE 5
PRINTING CONVENTIONS

Printing conventions
7KH,QWHU%DVHGRFXPHQWDWLRQVHWXVHVYDULRXVW\SRJUDSKLFFRQYHQWLRQVWRLGHQWLI\REMHFWV
DQGV\QWDFWLFHOHPHQWV
7KHIROORZLQJWDEOHOLVWVW\SRJUDSKLFFRQYHQWLRQVXVHGLQWH[WDQGSURYLGHVH[DPSOHVRIWKHLU
XVH

Convention Purpose Example


UPPERCASE SQL keywords, SQL functions, and names of all The following SELECT statement retrieves data from the
database objects such as tables, columns, CITY column in the CITIES table.
indexes, and stored procedures.
italic New terms, emphasized words, file names, and The isc4.gdb security database is not accessible
host- language variables. without a valid user name and password.
bold Utility names, user-defined and host-language Use gbak to back up and restore a database.
function names. Function names are always
Use the datediff() function to calculate the number of
followed by parentheses to distinguish them days between two dates.
from utility names.
TABLE 1.2 Text conventions

PROGRAMMER’S GUIDE 289


APPENDIX A INTERBASE DOCUMENT CONVENTIONS

Syntax conventions
7KHIROORZLQJWDEOHOLVWVWKHFRQYHQWLRQVXVHGLQV\QWD[VWDWHPHQWVDQGVDPSOHFRGHDQG
SURYLGHVH[DPSOHVRIWKHLUXVH

Convention Purpose Example


UPPERCASE Keywords that must be typed exactly as SET TERM !!;
they appear when used.
italic Parameters that cannot be broken into CREATE GENERATOR name;
smaller units. For example, a table name
cannot be subdivided.
<italic> Parameters in angle brackets that can be WHILE (<condition>) DO <compound_statement>
broken into smaller syntactic units.
[] Optional syntax: you do not need to CREATE [UNIQUE][ASCENDING|DESCENDING]
include anything that is enclosed in square
brackets.
{} One of the enclosed options must be {SMALLINT | INTEGER | FLOAT | DOUBLE PRECISION}
included in actual statement use. If the
contents are separated by a pipe symbol
(|), you must choose only one.
| You can choose only one of a group whose SET {DATABASE | SCHEMA}
elements are separated by this pipe SELECT [DISTINCT |ALL]
symbol.
When objects separated by this symbol
occur within curly brackets, you must
choose one; when they are within square
brackets you can choose one or none.
... The clause in brackets with this symbol can (<col> [,<col>…])
be repeated as many times as necessary.
TABLE 1.3 Syntax conventions

290 INTERBASE 5
Index

 DVWHULVN LQFRGH  YLHZV 


RSHUDWRU  $1'RSHUDWRU 
RSHUDWRU  $1<RSHUDWRU 
RSHUDWRU  $3,FDOOV
>@ EUDFNHWV DUUD\V ² %OREGDWD 
__RSHUDWRU  DSSHQGLQJWDEOHV 
²RSHUDWRU  DSSOLFDWLRQV 
6HHDOVR'64/DSSOLFDWLRQV
EXLOGLQJ 
A HYHQWKDQGOLQJ ²
DEVROXWHYDOXHV  SRUWLQJ 
DFFHVVPRGHSDUDPHWHU  SUHSURFHVVLQJ6HHJSUH
GHIDXOWWUDQVDFWLRQV  DULWKPHWLFH[SUHVVLRQV 
DFFHVVSULYLOHJHV6HHVHFXULW\ DULWKPHWLFIXQFWLRQV6HHDJJUHJDWHIXQFWLRQV
DFFHVVLQJ DULWKPHWLFRSHUDWRUV 
DUUD\V ² SUHFHGHQFH 
%OREGDWD  DUUD\HOHPHQWV 
GDWD  GHILQHG 
DFWLRQV6HHHYHQWV HYDOXDWLQJ 
DFWLYHGDWDEDVH  SRUWLQJ 
$GDSURJUDPV  UHWULHYLQJ 
DGGLQJ DUUD\,'V 
6HHDOVRLQVHUWLQJ DUUD\VOLFHV ²
FROXPQV  DGGLQJGDWD 
DGGLWLRQRSHUDWRU   GHILQHG 
DJJUHJDWHIXQFWLRQV  XSGDWLQJGDWD 
DUUD\VDQG  DUUD\V 
18//YDOXHV  6HHDOVRHUURUVWDWXVDUUD\
DOHUWHU HYHQWV  DFFHVVLQJ ²
DOLDVHV DJJUHJDWHIXQFWLRQV 
GDWDEDVH  FUHDWLQJ ²
WDEOHV  FXUVRUV ²
$/,*1PDFUR  '64/DSSOLFDWLRQVDQG 
$//NH\ZRUG  LQVHUWLQJGDWD 
$//RSHUDWRU  PXOWLGLPHQVLRQDO 
DOORFDWLQJPHPRU\  UHIHUHQFLQJ 
$/7(5,1'(; ² VHDUFKFRQGLWLRQV 
$/7(57$%/( ² VHOHFWLQJGDWD ²
$''RSWLRQ  VWRULQJGDWD 
'523RSWLRQ  VXEVFULSWV ²
DOWHULQJ 8')VDQG 
FROXPQGHILQLWLRQV ² XSGDWLQJ 
PHWDGDWD ² YLHZVDQG 

PROGRAMMER’S GUIDE i
$6&NH\ZRUG  EUDFNHWV >@ DUUD\V ²
DVFHQGLQJVRUWRUGHU  EXIIHUV
DVWHULVN LQFRGH  GDWDEDVHFDFKH ²
DWWDFKLQJWRGDWDEDVHV  %<9$/8(NH\ZRUG 
PXOWLSOH ² E\WHPDWFKLQJUXOHV 
DYHUDJHV 
$9* 
C
&ODQJXDJH
B FKDUDFWHUYDULDEOHV 
%$6('21  KRVWWHUPLQDWRU 
DUUD\VDQG  KRVWODQJXDJHYDULDEOHV ²
EDVLFBLRD  ZULWLQJIXQFWLRQPRGXOHV 
EDVLFBLRDGD  FDFKHEXIIHUV ²
%(*,1'(&/$5(6(&7,21  &$&+(NH\ZRUG 
%(7:((1RSHUDWRU  FDOFXODWLRQV 
127RSHUDWRUDQG  FDOOLQJ
ELQDU\ODUJHREMHFWV6HH%ORE 8')V ²
%ORE$3,IXQFWLRQV  FDVHLQVHQVLWLYHFRPSDULVRQV 
%OREGDWD ² FDVHVHQVLWLYHFRPSDULVRQV 
GHOHWLQJ  &$67NH\ZRUG 
ILOWHULQJ ² &$67 
LQVHUWLQJ ² &+$5GDWDW\SH
VHOHFWLQJ ² FRQYHUWLQJWR'$7( 
VWRULQJ  GHVFULSWLRQ 
XSGDWLQJ ² &+$59$5<,1*NH\ZRUG 
%/2%GDWDW\SH  &+$5$&7(5NH\ZRUG 
%OREGDWDW\SH  FKDUDFWHUVHWV
%OREILOWHUIXQFWLRQ  FRQYHUWLQJ 
DFWLRQPDFURGHILQLWLRQV ² GHIDXOW 
UHWXUQYDOXHV ² 121( 
%OREILOWHUV ² VSHFLI\LQJ 
H[WHUQDO  FKDUDFWHUVWULQJV
GHFODULQJ  FKDUDFWHUVWULPPLQJ 
ZULWLQJ  FRPSDULQJ 
LQYRNLQJ  OLWHUDOILOHQDPHV ²
WH[W  &+$5$&7(59$5<,1*NH\ZRUG 
W\SHV  FKDUDFWHUV
%OREVHJPHQWV ² WULPPLQJ 
%OREVXEW\SHV  FORVLQJ
%ORE8')V ² GDWDEDVHV ²
FRQWUROVWUXFWXUHV ² PXOWLSOH 
GHFODULQJ  WUDQVDFWLRQV ²
EOREBFRQFDWHQDWH  FRHUFLQJGDWDW\SHV 
EOREBJHWBVHJPHQW  &2//$7(FODXVH 
EOREBKDQGOH  FROODWLRQRUGHUV
EOREBSXWBVHJPHQW  *5283%<FODXVH 
%RROHDQH[SUHVVLRQV  25'(5%<FODXVH 
HYDOXDWLQJ  :+(5(FODXVH 
%RUODQG&&6HH&ODQJXDJH FROXPQQDPHV

ii INTERBASE 5
TXDOLI\LQJ  VSHFLI\LQJFKDUDFWHUVHWV 
YLHZV  &5($7('20$,1 ²
FROXPQPDMRURUGHU  DUUD\V 
FROXPQV &5($7(*(1(5$725 ²
DGGLQJ  &5($7(,1'(; ²
FRPSXWHG ² '(6&(1',1*RSWLRQ 
FUHDWLQJ  81,48(RSWLRQ 
GHILQLQJ &5($7(352&('85( 
DOWHULQJ ² &5($7(7$%/( ²
JOREDO  DUUD\V 
YLHZV  PXOWLSOHWDEOHV 
GURSSLQJ  &5($7(9,(: ²
VHOHFWLQJ ² :,7+&+(&.237,21 
HOLPLQDWLQJGXSOLFDWHV  FUHDWLQJ
VRUWLQJE\  DUUD\V ²
YDOXHVUHWXUQLQJ  FROXPQV 
&200,7 ² FRPSXWHGFROXPQV ²
PXOWLSOHGDWDEDVHV  LQWHJULW\FRQVWUDLQWV 
FRPSDULVRQRSHUDWRUV ² PHWDGDWD ²
18//YDOXHVDQG  8')V 
SUHFHGHQFH  &675,1*GDWDW\SH 
VXETXHULHV ² FXUVRUV 
&203,/(7,0(NH\ZRUG  DUUD\V ²
FRPSLOLQJ PXOWLSOHWUDQVDFWLRQSURJUDPV 
SURJUDPV ² VHOHFWSURFHGXUHV 
8')V 
FRPSXWHGFROXPQV
FUHDWLQJ ² D
GHILQHG  GDWD 
FRQFDWHQDWLRQRSHUDWRU __  DFFHVVLQJ 
&211(&7 ² '64/DSSOLFDWLRQV 
$//RSWLRQ  KRVWODQJXDJHYDULDEOHVDQG 
&$&+(RSWLRQ  FKDQJHV
HUURUKDQGOLQJ  FRPPLWWLQJ6HH&200,7
PXOWLSOHGDWDEDVHV ² UROOLQJEDFN6HH52//%$&.
RPLWWLQJ  GHILQLQJ 
6(7'$7$%$6(DQG  SURWHFWLQJ6HHVHFXULW\
FRQVWUDLQWV  UHWULHYLQJ
6HHDOVRVSHFLILFFRQVWUDLQWV RSWLPL]LQJ 
RSWLRQDO  VHOHFWLQJ 
&217$,1,1*RSHUDWRU  PXOWLSOHWDEOHV 
127RSHUDWRUDQG  VWRULQJ 
FRQYHUVLRQIXQFWLRQV ² GDWDVWUXFWXUHV
FRQYHUWLQJ %ORE ²
GDWDW\SHV  KRVWODQJXDJH 
GDWHV ² GDWDEDVHFDFKHEXIIHUV ²
LQWHUQDWLRQDOFKDUDFWHUVHWV  GDWDEDVHKDQGOHV 
&2817  '64/DSSOLFDWLRQV 
&5($7('$7$%$6( ² JOREDO 
LQ'64/  PXOWLSOHGDWDEDVHV ²

PROGRAMMER’S GUIDE iii


QDPLQJ  ORFNUHVROXWLRQSDUDPHWHU 
VFRSH  UROOLQJEDFN 
WUDQVDFWLRQVDQG  VWDUWLQJ ²
GDWDEDVHVSHFLILFDWLRQSDUDPHWHU  '(/(7(
GDWDEDVHV 8')V 
DWWDFKLQJWR  GHOHWLQJ6HHGURSSLQJ
PXOWLSOH ² '(6&NH\ZRUG 
FORVLQJ ² '(6&(1',1*NH\ZRUG 
FUHDWLQJ ² GHVFHQGLQJVRUWRUGHU 
GHFODULQJPXOWLSOH ²² GHWDFKLQJIURPGDWDEDVHV 
'64/DQGDWWDFKLQJ  GLUHFWRULHV
LQLWLDOL]LQJ ² VSHFLI\LQJ 
QDPLQJ  GLUW\UHDGV 
RSHQLQJ  ',6&211(&7 
UHPRWH  PXOWLSOHGDWDEDVHV 
GDWDW\SHV ² ',67,1&7NH\ZRUG 
FRHUFLQJ  GLYLVLRQRSHUDWRU  
FRPSDWLEOH  '//V
8')VDQG  8')VDQG 
FRQYHUWLQJ  GRPDLQV
'64/DSSOLFDWLRQV ² FUHDWLQJ ²
PDFURFRQVWDQWV ² '28%/(35(&,6,21GDWDW\SH 
'$7(GDWDW\SH '523,1'(; 
FRQYHUWLQJ  '5237$%/( ²
GHVFULSWLRQ  '5239,(: 
GDWHOLWHUDOV  GURSSLQJ
GDWHV  FROXPQV 
FRQYHUWLQJ ² PHWDGDWD ²
LQVHUWLQJ  '64/
VHOHFWLQJ  &5($7('$7$%$6( 
XSGDWLQJ  OLPLWDWLRQV 
'(&,0$/GDWDW\SH  PDFURFRQVWDQWV ²
GHFODUDWLRQVFKDQJLQJVFRSH  SURJUDPPLQJPHWKRGV ²
'(&/$5(&85625  UHTXLUHPHQWV ²
'(&/$5((;7(51$/)81&7,21 ² '64/DSSOLFDWLRQV 
'(&/$5(7$%/(  DFFHVVLQJGDWD 
GHFODULQJ DUUD\VDQG 
%OREILOWHUV  DWWDFKLQJWRGDWDEDVHV 
KRVWODQJXDJHYDULDEOHV ² FUHDWLQJGDWDEDVHV 
PXOWLSOHGDWDEDVHV ²² GDWDGHILQLWLRQVWDWHPHQWV 
RQHGDWDEDVHRQO\  GDWDEDVHKDQGOHV 
64/&2'(YDULDEOH  GDWDW\SHV ²
WUDQVDFWLRQQDPHV  GHIDXOWWUDQVDFWLRQV 
;64/'$V  H[HFXWLQJVWRUHGSURFHGXUHV 
GHIDXOWFKDUDFWHUVHW  PXOWLSOHWUDQVDFWLRQV 
GHIDXOWWUDQVDFWLRQV SRUWLQJ 
DFFHVVPRGHSDUDPHWHU  SUHSURFHVVLQJ 
GHIDXOWEHKDYLRU  SURJUDPPLQJUHTXLUHPHQWV ²
'64/DSSOLFDWLRQV  64/VWDWHPHQWV
LVRODWLRQOHYHOSDUDPHWHU  HPEHGGHG 

iv INTERBASE 5
WUDQVDFWLRQQDPHV ² 127RSHUDWRUDQG 
WUDQVDFWLRQV  H[SUHVVLRQEDVHGFROXPQV6HHFRPSXWHGFROXPQV
ZULWLQJ  H[SUHVVLRQV 
;64/'$V ² HYDOXDWLQJ 
'64/OLPLWDWLRQV ² H[WHQGHG64/GHVFULSWLRUDUHDV6HH;64/'$V
'64/VWDWHPHQWV  (;7(51NH\ZRUG ²
G\QDPLFOLQNOLEUDULHV6HH'//V
G\QDPLF64/6HH'64/
F
ILOHQDPHV
E VSHFLI\LQJ ²
(1''(&/$5(6(&7,21  ILOHV
HUURUFRGHVDQGPHVVDJHV  6HHDOVRVSHFLILFILOHV
FDSWXULQJ ² VRXUFHVSHFLI\LQJ 
GLVSOD\LQJ  )/2$7GDWDW\SH 
HUURUVWDWXVDUUD\  IQBDEV 
HUURUKDQGOLQJURXWLQHV  IQBGDWHGLII 
FKDQJLQJ  IQBWULP 
GLVDEOLQJ  )520NH\ZRUG ²
JXLGHOLQHV ² IXQFWLRQV
QHVWLQJ  DJJUHJDWH 
WHVWLQJ64/&2'(GLUHFWO\  FRQYHUVLRQ ²
:+(1(9(5DQG ² HUURUKDQGOLQJ 
HUURUV  QXPHULF 
UXQWLPH XVHUGHILQHG6HH8')V
UHFRYHULQJIURP 
WUDSSLQJ 
XQH[SHFWHG  G
XVHUGHILQHG6HHH[FHSWLRQV *(1B,' 
(6&$3(NH\ZRUG  JHQHUDWRUV
(9(17,1,7  FUHDWLQJ ²
PXOWLSOHHYHQWV  GHILQHG 
(9(17:$,7 ² JOREDOFROXPQGHILQLWLRQV 
HYHQWV ² JOREDOGDWDEDVHKDQGOHV 
6HHDOVRWULJJHUV JSUH ²
DOHUWHU  FRPPDQGOLQHRSWLRQV ²
GHILQHG  GDWDEDVHVVSHFLI\LQJ 
PDQDJHU  '64/DSSOLFDWLRQV 
PXOWLSOH ² KDQGOLQJWUDQVDFWLRQV 
QRWLI\LQJDSSOLFDWLRQV ² ODQJXDJHRSWLRQV 
SRVWLQJ  ILOHQDPHVYV ²
UHVSRQGLQJWR  PVZLWFK 
H[HFXWDEOHREMHFWV  SURJUDPPLQJUHTXLUHPHQWV 
H[HFXWDEOHSURFHGXUHV ² VSHFLI\LQJVRXUFHILOHV 
'64/  VTOGDROGVZLWFK 
LQSXWSDUDPHWHUV ² V\QWD[ 
(;(&87(  JURXSDJJUHJDWHV 
(;(&87(,00(',$7(  JURXSLQJURZV 
(;(&87(352&('85(  UHVWULFWLRQV 
(;,676RSHUDWRU 

PROGRAMMER’S GUIDE v
H ,17(*(5GDWDW\SH 
KDUGFRGHGVWULQJV LQWHJULW\FRQVWUDLQWV 
ILOHQDPHV ² 6HHDOVRVSHFLILFW\SH
+$9,1*NH\ZRUG  RSWLRQDO 
KHDGHUILOHV6HHLEDVHK ,QWHUDFWLYH64/6HHLVTO
KRVWODQJXDJHV  LQWHUEDVHD 
GDWDVWUXFWXUHV  LQWHUEDVHDGD 
KRVWODQJXDJHYDULDEOHV  LQWHUQDWLRQDOFKDUDFWHUVHWV 
DUUD\V  ,172NH\ZRUG 
GHFODULQJ ² ,618//RSHUDWRU 
VSHFLI\LQJ  127RSHUDWRUDQG 
KRVWVVSHFLI\LQJ  LVFBEOREBFWO 
ILHOGGHVFULSWLRQV 
LVFBEOREBGHIDXOWBGHVF 
I LVFBEOREBJHQBESE 
,26HHLQSXWRXWSXW LVFBEOREBLQIR 
LEDVHK  LVFBEOREBORRNXSBGHVF 
LQFOXGLQJ  LVFBEOREBVHWBGHVF 
LGHQWLILHUV  LVFBFDQFHOBEORE 
GDWDEDVHKDQGOHV  LVFBFORVHBEORE 
GDWDEDVHV  LVFBFUHDWHBEORE 
YLHZV  LVFBGHFRGHBGDWH 
,1RSHUDWRU  LVFBHQFRGHBGDWH 
127RSHUDWRUDQG  LVFBJHWBVHJPHQW 
,1'(;NH\ZRUG  LVFBLQWHUSUHWH ²
LQGH[HV LVFBRSHQBEORE 
DOWHULQJ ² LVFBSULQWBVTOHUURU 
FUHDWLQJ ² LVFBSXWBVHJPHQW 
GURSSLQJ  ,6&B48$'VWUXFWXUH ²
SUHYHQWLQJGXSOLFDWHHQWULHV  LVFBVTOBLQWHUSUHWH 
SULPDU\NH\V  LVFBVWDWXV 
VRUWRUGHU  LVRODWLRQOHYHOSDUDPHWHU 
FKDQJLQJ  GHIDXOWWUDQVDFWLRQV 
V\VWHPGHILQHG 
XQLTXH 
,1',&$725NH\ZRUG  J
LQGLFDWRUYDULDEOHV  -2,1NH\ZRUG 
18//YDOXHV  MRLQV 
LQLWLDOL]LQJ
GDWDEDVHV ²
WUDQVDFWLRQQDPHV  K
LQSXWSDUDPHWHUV ² NH\FRQVWUDLQWV6HH)25(,*1.(<FRQVWUDLQWV
6HHDOVRVWRUHGSURFHGXUHV 35,0$5<.(<FRQVWUDLQWV
,16(57 NH\V
DUUD\V  SULPDU\ 
8')V 
LQVHUWLQJ
6HHDOVRDGGLQJ L
%OREGDWD ² ODQJXDJHRSWLRQV JSUH 
GDWHV  ILOHQDPHVYV ²

vi INTERBASE 5
OHDGLQJFKDUDFWHUV  FORVLQJ 
OLEUDULHV GDWDEDVHKDQGOHV ²
G\QDPLFOLQN6HH'//V GHFODULQJ ²²
8')VDQG  GHWDFKLQJ 
8QL[SODWIRUPV  RSHQLQJ 
/,.(RSHUDWRU  WUDQVDFWLRQV 
127RSHUDWRUDQG  PXOWLSOHWDEOHV
OLPERWUDQVDFWLRQV  FUHDWLQJ 
OLQNLQJ VHOHFWLQJGDWD 
SURJUDPV ² PXOWLSOHWUDQVDFWLRQV 
OLWHUDOVWULQJVILOHQDPHV ² '64/DSSOLFDWLRQV 
OLWHUDOV\PEROV  UXQQLQJ ²
ORFNUHVROXWLRQSDUDPHWHU  PXOWLSOLFDWLRQRSHUDWRU 
GHIDXOWWUDQVDFWLRQV  PXOWLURZVHOHFWV ²
ORJLFDORSHUDWRUV ²
SUHFHGHQFH 
ORRSV6HHUHSHWLWLYHVWDWHPHQWV N
ORVWXSGDWHV  QDPHGWUDQVDFWLRQV 
VWDUWLQJ 
QDPHV
M FROXPQ 
PVZLWFK  TXDOLI\LQJ 
PDFURFRQVWDQWV ² LQ6(/(&7VWDWHPHQWV 
PDNHOLE  VSHFLI\LQJDWUXQWLPH 
PDWKHPDWLFDORSHUDWRUV  QDPLQJ
SUHFHGHQFH  GDWDEDVHKDQGOHV 
0$;  GDWDEDVHV 
PD[BVHJOHQ  WUDQVDFWLRQV ²
PD[LPXPYDOXHV  YLHZV 
PHPRU\ 1$785$/NH\ZRUG 
DOORFDWLQJ  125(&25'B9(56,21 
PHWDGDWD  12:$,7 
DOWHULQJ ² 121(FKDUDFWHUVHWRSWLRQ 
FUHDWLQJ ² QRQUHSURGXFLEOHUHDGV 
GURSSLQJ ² 127RSHUDWRU 
IDLOLQJ  %(7:((1RSHUDWRUDQG 
0LFURVRIW&&6HH&ODQJXDJH &217$,1,1*RSHUDWRUDQG 
0,1  (;,676RSHUDWRUDQG 
PLQLPXPYDOXHV  ,1RSHUDWRUDQG 
PRGLI\LQJ6HHDOWHULQJXSGDWLQJ ,618//RSHUDWRUDQG 
PRGXOHV /,.(RSHUDWRUDQG 
REMHFW  6,1*8/$5RSHUDWRUDQG 
8')V  67$57,1*:,7+RSHUDWRUDQG 
PXOWLFROXPQVRUWV  12: 
PXOWLGLPHQVLRQDODUUD\V 12:GDWHOLWHUDO 
FUHDWLQJ  18//YDOXHV
VHOHFWLQJGDWD  DJJUHJDWHIXQFWLRQV 
PXOWLPRGXOHSURJUDPV  DUUD\VDQG 
PXOWLSOHGDWDEDVHV FRPSDULVRQV 
DWWDFKLQJWR ² LQGLFDWRUYDULDEOHV 

PROGRAMMER’S GUIDE vii


QXPEHUBVHJPHQWV  35(3$5( 
QXPEHUV SUHSURFHVVRU6HHJSUH
DEVROXWHYDOXHV  35,0$5<.(<FRQVWUDLQWV 
JHQHUDWLQJ  SULPDU\NH\V 
180(5,&GDWDW\SH  SULYLOHJHV6HHVHFXULW\
FRQYHUWLQJWR'$7(  SURFHGXUHV6HHVWRUHGSURFHGXUHV
QXPHULFIXQFWLRQ  SURJUDPPLQJ
QXPHULFYDOXHV6HHYDOXHV '64/DSSOLFDWLRQV ²
JSUH 
SURJUDPV
O FRPSLOLQJDQGOLQNLQJ ²
REMHFWPRGXOHV  SURMHFWLRQ GHILQHG 
RSHQLQJ 3527(&7('5($' 
GDWDEDVHV  3527(&7(':5,7( 
PXOWLSOH  SURWHFWLQJGDWD6HHVHFXULW\
RSHUDWRUV
DULWKPHWLF 
FRPSDULVRQ ² Q
FRQFDWHQDWLRQ  TXDOLI\ GHILQHG 
ORJLFDO ² TXHULHV 
SUHFHGHQFH ² 6HHDOVR64/
FKDQJLQJ  HOLPLQDWLQJGXSOLFDWHFROXPQV 
VWULQJ  JURXSLQJURZV 
RSWLPL]LQJ PXOWLFROXPQVRUWV 
GDWDUHWULHYDO  UHVWULFWLQJURZVHOHFWLRQ 
25RSHUDWRU  VHDUFKFRQGLWLRQV ²²
25'(5NH\ZRUG  DUUD\VDQG 
RUGHURIHYDOXDWLRQ RSHUDWRUV ² FRPELQLQJVLPSOH 
FKDQJLQJ  UHYHUVLQJ 
RXWSXWSDUDPHWHUV VHOHFWLQJPXOWLSOHURZV ²
6HHDOVRVWRUHGSURFHGXUHV VHOHFWLQJVLQJOHURZV 
VRUWLQJURZV 
VSHFLILFWDEOHV ²
P ZLWKMRLQV 
SDUDPHWHUV TXHU\RSWLPL]HU 
DFFHVVPRGH 
GDWDEDVHVSHFLILFDWLRQ 
LVRODWLRQOHYHO  R
ORFNUHVROXWLRQ  5($'&200,77(' 
WDEOHUHVHUYDWLRQ  UHDGRQO\YLHZV 
8')V  5(&25'B9(56,21 
XQNQRZQ  UHPRWHGDWDEDVHV 
SKDQWRPURZV  5(6(59,1*FODXVH 
3/$1NH\ZRUG  WDEOHUHVHUYDWLRQRSWLRQV 
SRUWLQJ UHVXOWWDEOHV 
DSSOLFDWLRQV  6HHDOVRMRLQV
DUUD\V  52//%$&. 
3267B(9(17  PXOWLSOHGDWDEDVHV 
SUHFHGHQFHRIRSHUDWRUV ² UROOEDFNV 
FKDQJLQJ  URXWLQHV 

viii INTERBASE 5
6HHDOVRHUURUKDQGOLQJURXWLQHV /,.(RSHUDWRU 
URZPDMRURUGHU  6,1*8/$5RSHUDWRU 
URZV 620(RSHUDWRU 
FRXQWLQJ  67$57,1*:,7+RSHUDWRU 
JURXSLQJ  VHOHFWSURFHGXUHV ²
UHVWULFWLRQV  FDOOLQJ 
VHOHFWLQJ  FXUVRUV 
PXOWLSOH ² LQSXWSDUDPHWHUV 
VLQJOH  VHOHFWLQJ 
VRUWLQJ  WDEOHVYV 
UXQWLPHHUURUV YLHZVYV 
UHFRYHULQJIURP  6(/(&7VWDWHPHQWV
5817,0(NH\ZRUG  VLQJOHWRQ6(/(&7V 
VHOHFWLQJ
%OREGDWD ²
S FROXPQV ²
VFLHQWLILFQRWDWLRQ  GDWD 
VFRSH 6HHDOVR6(/(&7
FKDQJLQJ  GDWHV 
GDWDEDVHKDQGOHV  PXOWLSOHURZV ²
:+(1(9(5  VLQJOHURZV 
VHDUFKFRQGLWLRQV TXHULHV ²² YLHZV 
DUUD\VDQG  6(7'$7$%$6( 
FRPELQLQJVLPSOH  &203,/(7,0(RSWLRQ 
UHYHUVLQJ  &211(&7DQG 
6(/(&7 ²² '64/DSSOLFDWLRQV 
DUUD\V ² (;7(51RSWLRQ ²
&$67FODXVH  PXOWLSOHGDWDEDVHVDQG 
&5($7(9,(:DQG  RPLWWLQJ 
',67,1&7RSWLRQ  5817,0(RSWLRQ 
)520FODXVH ² 67$7,&RSWLRQ ²
*5283%<FODXVH ² 6(71$0(6 
FROODWLRQRUGHU  6(775$16$&7,21 ²
+$9,1*FODXVH  DFFHVVPRGHSDUDPHWHU 
,172RSWLRQ  SDUDPHWHUV 
25'(5%<FODXVH  V\QWD[ 
FROODWLRQRUGHU  6+$5('5($' 
3/$1FODXVH  6+$5(':5,7( 
75$16$&7,21RSWLRQ  VLQJOHWRQ6(/(&7V 
8')V  GHILQHG 
:+(5(FODXVH ²² 6,1*8/$5RSHUDWRU 
$//RSHUDWRU  127RSHUDWRUDQG 
$1<RSHUDWRU  60$//,17GDWDW\SH 
%(7:((1RSHUDWRU  61$36+27 
&$67RSWLRQ  61$36+277$%/(67$%,/,7< 
FROODWLRQRUGHU  620(RSHUDWRU 
&217$,1,1*RSHUDWRU  62570(5*(NH\ZRUGV 
(;,676RSHUDWRU  VRUWRUGHU
,1RSHUDWRU  DVFHQGLQJ 
,618//RSHUDWRU  GHVFHQGLQJ 

PROGRAMMER’S GUIDE ix
LQGH[HV  V\VWHPWDEOHV 
TXHULHV  V\VWHPGHILQHGLQGH[HV 
VWLFN\ 
VRUWLQJ
PXOWLSOHFROXPQV  T
URZV  WDEOHQDPHV
VRXUFHILOHV  DOLDVHV 
VSHFLI\LQJ GXSOLFDWLQJ 
FKDUDFWHUVHWV  LGHQWLFDO 
GLUHFWRULHV  WDEOHUHVHUYDWLRQSDUDPHWHU 
ILOHQDPHV ² WDEOHV
KRVWODQJXDJHYDULDEOHV  DOWHULQJ ²
KRVWV  DSSHQGLQJZLWK81,21 
64/VWDWHPHQWV FUHDWLQJ ²
'64/DSSOLFDWLRQV  PXOWLSOH 
VWULQJV  GHFODULQJ 
64/&2'(YDULDEOH GURSSLQJ ²
GHFODULQJ  TXDOLI\LQJ 
H[DPLQLQJ  TXHU\LQJVSHFLILF ²
UHWXUQYDOXHV  VHOHFWSURFHGXUHVYV 
GLVSOD\LQJ  WLPHVWUXFWXUHV 
WHVWLQJ  WLPHK 
64/'$V  72'$< 
SRUWLQJDSSOLFDWLRQVDQG  72'$<GDWHOLWHUDO 
VWDUWLQJGHIDXOWWUDQVDFWLRQV ² 7202552: 
67$57,1*:,7+RSHUDWRU  WRWDOBVL]H 
127RSHUDWRUDQG  WRWDOVFDOFXODWLQJ 
VWDWHPHQWV WUDLOLQJFKDUDFWHUV 
6HHDOVR'64/VWDWHPHQWV64/VWDWHPHQWV 75$16$&7,21NH\ZRUG 
GDWDGHILQLWLRQ  WUDQVDFWLRQPDQDJHPHQWVWDWHPHQWV 
GDWDVWUXFWXUHVDQG  WUDQVDFWLRQQDPHV 
HPEHGGHG  GHFODULQJ 
HUURUKDQGOLQJ  '64/DSSOLFDWLRQV ²
WUDQVDFWLRQPDQDJHPHQW  LQLWLDOL]LQJ 
67$7,&NH\ZRUG ² PXOWLWDEOH6(/(&7V 
VWDWXVDUUD\6HHHUURUVWDWXVDUUD\ WUDQVDFWLRQV 
VWLFN\VRUWRUGHU  DFFHVVLQJGDWD 
VWRUHGSURFHGXUHV ² FORVLQJ ²
GHILQHG  FRPPLWWLQJ 
UHWXUQYDOXHV  GDWDEDVHKDQGOHVDQG 
YDOXHV  GHIDXOW ²
;64/'$VDQG  UROOLQJEDFN 
VWULQJRSHUDWRU __  '64/DSSOLFDWLRQV 
VXETXHULHV HQGLQJ 
FRPSDULVRQRSHUDWRUV ² PXOWLSOHGDWDEDVHV 
GHILQHG  QDPHG 
VXEVFULSWV DUUD\V ² VWDUWLQJ 
VXEWUDFWLRQRSHUDWRU   QDPLQJ ²
680  UROOLQJEDFN 
6XQ26SODWIRUPV  UXQQLQJPXOWLSOH ²

x INTERBASE 5
XQQDPHG  V
WUDSSLQJ YDOXHV
HUURUV  6HHDOVR18//YDOXHV
WULJJHUV  DEVROXWH 
75,0  FRPSDULQJ 
PDQLSXODWLQJ 
PDWFKLQJ 
U PD[LPXP 
XGIOLEF  PLQLPXP 
8')V VHOHFWLQJ 
DUUD\VDQG  VWRUHGSURFHGXUHV 
%ORE ² 8')V 
FDOOLQJ ² XQLTXH 
FRPSLOLQJ  XQNQRZQWHVWLQJIRU 
FUHDWLQJ  9$5&+$5GDWDW\SH 
GHFODULQJ ² YDULDEOHV
GHILQHG  KRVWODQJXDJH 
LQVHUWLQJ  DUUD\V 
OLEUDULHV  GHFODULQJ ²
FKDQJLQJ  VSHFLI\LQJ 
PRGXOHV  LQGLFDWRU 
SDUDPHWHUV  18//YDOXHV 
UHWXUQYDOXHV  YLHZV 
VHOHFWLQJ  DOWHULQJ 
XSGDWLQJ  DUUD\VDQG 
XQH[SHFWHGHUURUV  FUHDWLQJ ²
81,21 GHILQLQJFROXPQV 
DSSHQGLQJWDEOHV  GURSSLQJ 
LQ6(/(&7VWDWHPHQWV  QDPLQJ 
XQLTXHLQGH[HV  UHDGRQO\ 
81,48(NH\ZRUG  VHOHFWSURFHGXUHVYV 
XQLTXHYDOXHV  VHOHFWLQJ 
8QL[SODWIRUPV  XSGDWDEOH 
XQNQRZQYDOXHV YLUWXDOWDEOHV 
WHVWLQJIRU 
XQUHFRYHUDEOHHUURUV 
XSGDWDEOHYLHZV  W
83'$7( :$,7 
DUUD\V  :+(1(9(5 ²
GDWHV  HPEHGGLQJ 
8')V  OLPLWDWLRQV 
XSGDWHVLGHHIIHFWV  VFRSH 
XSGDWLQJ :+(5(FODXVH6HH6(/(&7
6HHDOVRDOWHULQJ :+(5(NH\ZRUG 
%OREGDWD ² ZLOGFDUGV
833(5  VWULQJFRPSDULVRQV 
XVHUGHILQHGIXQFWLRQV6HH8')V ZULWLQJH[WHUQDO%OREILOWHUV 
86,1*FODXVH 

PROGRAMMER’S GUIDE xi
X
;64/'$B/(1*7+PDFUR 
;64/'$V ²
GHFODULQJ 
ILHOGV 
LQSXWGHVFULSWRUV 
RXWSXWGHVFULSWRUV 
SRUWLQJDSSOLFDWLRQVDQG 
VWRUHGSURFHGXUHVDQG 
VWUXFWXUHV 
;64/9$5VWUXFWXUH 
ILHOGV 

Y
<(67(5'$< 

xii INTERBASE 5

You might also like