サンプルをつくるぜ 第3弾
updateやinsertはそれ自体が「処理」であり「処理の呼び出し」であるからして、
メソッド構成はqueryToResultSetみたいに実処理呼び出し型になる。
<クラス編>
(1)1つに付き1種類しか役割を持たないクラス
(2) (1)をいくつかまとめているだけのクラス
の役割で言うとさっきの
(1)「Selectを投げる役割」のクラス
を
(1)「SQL文を投げる役割」のクラス
に変更する。
// やっぱり省くぜヘッダコメント
public abstract class GenericSQL {
// 省略:ヘッダコメント!
public String createSQL(){
// 実装はサブクラスにて行うこと
}
// 省略:ヘッダコメント
public RecordSet executeQuery( String strSQL ){
// 実装はサブクラスにて
}
// 省略
public RecordSet arrangesData( RecordSet rsItem ){
// 実装はサ(ry
}
// 略
public boolean executeUpdate(){
// 実装(ry
}
// 略
public boolean executeInsert(){
// 実(ry
}
//
public boolean executeDelete(){
// (ry
}
//
private boolean execute( String strSQL ){
// (ry
}
// ry
public String createSQLUpdate(){
// (ry
}
// ry
public String createSQLInsert(){
// (ry
}
// ry
public String createSQLDelete(){
// (ry
}
}
とりあえずカタチをすぐには変えずに踏襲してみはするものの、
SQLまで埋め込んでしまうとやっぱり1種類のことしか出来なくなるのはよろしくない。
処理パラメータでも渡してしまえば一挙に解決(・∀・)!
っと思いたくなるところだが、
「SQLを作る」と「処理を実行する」という二つの役割が如実に分かれるようになる。
役割が分れたらクラスもわけましょう。
ってことで、「処理を実行する」役割の「ExecuteSQL」と、
「SQLを作る」役割の「MasterBase」を作る。
が、ちょっとまってほしい。
SQLを作るのは各マスタに依存する事ではないか?
であれば各マスタが実装しているほうがよいのではないか?
・・・・・・
アサピー節はおいらにゃ難しかったことを思い知りつつも、
MasterBaseはイメージベースでつくることにする。
いくつSelectを発行するのか、いくつUpdateを発行するのかは構成時の自由だからである。
// 省いていいよねヘッダコメント
public class ExecuteSQL {
// Select発行用
public RecordSet queryToResultSet( String strSQL ){
// 実装はこのクラスにて
RecordSet rs = null; // 戻り値作成用
try {
// ry
} catch( Exception ex ){
// ry
}
return rs;
}
// Insert、Update、Delete発行用
public boolean execute( String strSQL ){
// 実装はこのクラスにて
boolen boolRtn = false; // 戻り値作成用
try {
// ry
boolRtn = true; // ここまできたら成功
} catch( Exception ex ){
boolRtn = false; // 絶対エラー
}
return boolRtn;
}
}
2つのSelect、1つずつのInsert、Update、Deleteを投げるMasterBaseはこんなカタチ。
// やっぱり省くぜヘッダコメント
public class MasterBase extends ExecuteSQL{
// 1つ目のSelect
public RecordSet queryTo_Part01(){
String strSQL = createSQLSelect01();
return super.queryToResultSet( strSQL );
}
// 1つ目のSelectのSQL文
private String createSQLSelect01(){
//(略)
}
// 2つ目のSelect
public RecordSet queryTo_Part02(){
String strSQL = createSQLSelect02();
RecordSet rs = super.queryToResultSet( strSQL );
return arrangesData( rs );
}
// 1つ目のSelectのSQL文
private String createSQLSelect02(){
//(略)
}
// 省略
private RecordSet arrangesData( RecordSet rsItem ){
// 実装は(ry
}// 唯一のUpdate
public boolean executeUpdate(){
String strSQL = createSQLUpdate();
return super.execute( strSQL );
}
// ↑のSQL文
private String createSQLUpdate(){
//(略)
}// 唯一のInsert
public boolean executeInsert(){
String strSQL = createSQLInsert();
return super.execute( strSQL );
}
// ↑のSQL文
private String createSQLInsert(){
//(略)
}// 唯一のDelete
public boolean executeDelete(){
String strSQL = createSQLDelete();
return super.execute( strSQL );
}
// ↑のSQL文
private String createSQLDelete(){
//(略)
}
}
また、SQL文そのものを外部からもらう形式にすると、こんな感じで作れたりしますが、
SQLがハイブリッド結合になるような気もします。
// いつも通りのヘッダコメント
public class MasterBase extends ExecuteSQL{String _strSQL;
public void setSQL( String value ){
_strSQL = value;
}// Select
public RecordSet queryTo(){
return super.queryToResultSet( _strSQL );
}
// Update
public boolean executeUpdate(){
return super.execute( _strSQL );
}
// Insert
public boolean executeInsert(){
return super.execute( _strSQL );
}
// Delete
public boolean executeDelete(){
return super.execute( _strSQL );
}
}
作ってみたらあれですな。
ものすごいポリモルフィズムを実現しているように見えてきますが、
こんな多態性いらない。
やってることがSuperクラスそのまんまならコード量が増えてクラス数が増えるだけ害となるのがその理由。
物は試しで作ってみて、ロクな結果にならなかったら作る前に戻ろう。
「MasterBase」のような形式でEmployeeMasterやその他を作る事にすれば
Superクラスは間違うことなく多態性ばっちりな状態といえるだろう。