重要なお知らせ

「教えて! goo」は2025年9月17日(水)をもちまして、サービスを終了いたします。詳細はこちら>

電子書籍の厳選無料作品が豊富!

以下のようにプログラムを作成した場合に
疑問点がありますので、ご教授願います。

public class Sample extends HttpServlet{
 private static final int int_OK = 0; // 戻り値(OK)
 private Stringname;   // 名前
 private Stringdb_name; // DB名前

protected void doPost(HttpServletRequest req,HttpServletResponse res)
throws ServletException, IOException{

 // リクエストパラメータ取得
 name = req.getParameter("name");// 名前
 // DB検索
 db_name = rs.getString("name");
 // 結果を返却
 }
}

【疑問点】
 (1) 排他制御やスレッドを行っていません。
  ・変数はすべてprivate宣言していますが、
  同時アクセスが行われた際の変数はどのようになるのでしょうか?
 (2) SingleThreadModelを実装した際はどのような動きになりますでしょうか?

不足点などあるかと思いますが、よろしくお願いします。

A 回答 (3件)

No.2です。


だとしたら、引数で渡した方がいいと思います。
もし数が多いようであれば、データに対応するクラスを1つ作って渡せばいいと思います。

なぜなら。
せっかくサーブレットというマルチスレッドのものを使っているのに、わざわざシングルスレッドにして、アクセス数に比例してユーザーの応答時間を長くする必要はないと思うので。

また、せっかくDBという排他制御の備わったものを使っているのに(お使いのDBが何かはわかりませんが、まず間違いないでしょう)、わざわざパフォーマンス落とす必要もないと思います(ファイルの読み書きでデータを拾っているのならともかく)。

この回答への補足

ご回答ありがとうございます。
また、お礼が遅くなりまして申し訳ありません。
ここでまたひとつ質問ですが、
クラスを作成した場合はそのクラスはpublicになると思いますが、
同時にdoPostの要求がきた場合は値が書き換わることはないのでしょうか?

補足日時:2006/11/10 20:14
    • good
    • 0
この回答へのお礼

お礼の欄にすみせん。
上記の内容が間違っていましたので訂正します。

public class Sample extends HttpServlet{
 private static final int int_OK = 0; // 戻り値(OK)
// private String name;   // 名前
// private String db_name;  // DB名前

protected void doPost(HttpServletRequest req,HttpServletResponse res)
throws ServletException, IOException{

 SetterGetter setget = new SetterGetter();
 // リクエストパラメータ取得
 setget.name = req.getParameter("name"); // 名前
 // DB検索
 setget.db_name = rs.getString("name");
 // 結果を返却

private class SetterGetter{
   private String name;   // 名前
   private String db_name;  // DB名前

 private void setName(String name) {
    this.name= name;
 }
 private String getName() {
    return name;
 }
 private void setDb_name(String db_name) {
    this.db_name = db_name;
 }
 private String getDb_name() {
    return db_name;
 }
}
}
以下の処理で問題なく動作しますでしょうか?
よろしくお願いします。

お礼日時:2006/11/10 21:30

クラスメンバ変数でなく、doPostの中でのローカル変数にすれば、何も問題ないと思うのですが・・・?

この回答への補足

ご回答ありがとうございます。
申し訳ありません。内容に不足がありました。
すべての処理をdoPostの中で行っていたら上記の内容で良いかと思いますが、メソッドを作成して処理のやりとりを行っています。
ローカル変数にした場合、必要な情報を引数で渡さなくてはなりませんので、今回クラスメンバ変数を使用しています。

補足日時:2006/10/19 17:44
    • good
    • 0

(1)


サーブレットのインスタンスは1つです。
複数から同時アクセスされると、
タイミングによってはname、db_nameの値が後から(最後に)検索された値に上書きされてしまいます。

(2)
(自信がありません。)
JavaDocには
「Servlet が一度に一つのリクエストだけを扱うことを保証します。」
とありますので、複数から同時アクセスされても、
実行されるリクエストは1つになり、変数が上書きされることはないと思います。
が、他のリクエストは、その間待つことになるので、頻繁に複数からアクセスされる場合は
パフォーマンスが落ちてしまうと思います。

Servlet API バージョン2.4では推奨されていないようです。
----------------------------------------------------------------------
SingleThreadModel がすべてのスレッドセーフの問題を解決するというわけではないことに注意してください。
例えば、SingleThreadModel の Servlet を使用する場合、複数のスレッドに対する複数の要求で、
同時にセッション属性と静的な変数にアクセスすることができます。
開発者はこのインタフェースを実装する代わりにインスタンス変数の使用を避ける、
あるいはそれらのリソースにアクセスするコードブロックを同期させるなどのように問題を解決する他の手段を取ることをお勧めします。
このインタフェースは Servlet API バージョン 2.4 では推奨されません。
----------------------------------------------------------------------

この回答への補足

ご回答ありがとうございます。

やはり(1)は予想していた通りでした。
いろいろ調べて(2)を使用しようと思ったのですが
自信がなくて質問させていただきました。

補足日時:2006/10/19 17:39
    • good
    • 0

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!