• ベストアンサー
※ ChatGPTを利用し、要約された質問です(原文:同時アクセス時の動作)

同時アクセス時の動作に関する疑問点

このQ&Aのポイント
  • 質問文章では、同時アクセス時の動作についての疑問が述べられています。
  • 特に、プログラム内での排他制御やスレッド処理が行われていないため、同時アクセス時における変数の挙動や結果についての不安があります。
  • また、SingleThreadModelを実装した場合の動作についても疑問があります。

質問者が選んだベストアンサー

  • ベストアンサー
noname#45950
noname#45950
回答No.3

No.2です。 だとしたら、引数で渡した方がいいと思います。 もし数が多いようであれば、データに対応するクラスを1つ作って渡せばいいと思います。 なぜなら。 せっかくサーブレットというマルチスレッドのものを使っているのに、わざわざシングルスレッドにして、アクセス数に比例してユーザーの応答時間を長くする必要はないと思うので。 また、せっかくDBという排他制御の備わったものを使っているのに(お使いのDBが何かはわかりませんが、まず間違いないでしょう)、わざわざパフォーマンス落とす必要もないと思います(ファイルの読み書きでデータを拾っているのならともかく)。

-cinq-
質問者

お礼

お礼の欄にすみせん。 上記の内容が間違っていましたので訂正します。 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;  } } } 以下の処理で問題なく動作しますでしょうか? よろしくお願いします。

-cinq-
質問者

補足

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

全文を見る
すると、全ての回答が全文表示されます。

その他の回答 (2)

noname#45950
noname#45950
回答No.2

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

-cinq-
質問者

補足

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

全文を見る
すると、全ての回答が全文表示されます。
回答No.1

(1) サーブレットのインスタンスは1つです。 複数から同時アクセスされると、 タイミングによってはname、db_nameの値が後から(最後に)検索された値に上書きされてしまいます。 (2) (自信がありません。) JavaDocには 「Servlet が一度に一つのリクエストだけを扱うことを保証します。」 とありますので、複数から同時アクセスされても、 実行されるリクエストは1つになり、変数が上書きされることはないと思います。 が、他のリクエストは、その間待つことになるので、頻繁に複数からアクセスされる場合は パフォーマンスが落ちてしまうと思います。 Servlet API バージョン2.4では推奨されていないようです。 ---------------------------------------------------------------------- SingleThreadModel がすべてのスレッドセーフの問題を解決するというわけではないことに注意してください。 例えば、SingleThreadModel の Servlet を使用する場合、複数のスレッドに対する複数の要求で、 同時にセッション属性と静的な変数にアクセスすることができます。 開発者はこのインタフェースを実装する代わりにインスタンス変数の使用を避ける、 あるいはそれらのリソースにアクセスするコードブロックを同期させるなどのように問題を解決する他の手段を取ることをお勧めします。 このインタフェースは Servlet API バージョン 2.4 では推奨されません。 ----------------------------------------------------------------------

-cinq-
質問者

補足

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

全文を見る
すると、全ての回答が全文表示されます。

関連するQ&A

  • 宣言のタイミング

    質問させてください。 Servletの中で、他クラスからの参照のできる static final String について何ですが、 例えば、 public class goo extends HttpServlet{ static final String CODE = "text/html;charset=Shift_JIS"; public void doPost(HttpServletRequest req,HttpServletResponse res) thows servletException,IOException{ res.setContentType(CODE); など、実際の値を入れるやり方は、分かるのですが、 Servlet内で、何らかの処理後の String を static final String 宣言をするには、どうしたらよいのでしょうか? 例えば、 public class goo extends HttpServlet{ public void doPost(HttpServletRequest req,HttpServletResponse res) thows servletException,IOException{ String para = req.getParameter(para); String param = new String(para.getBytes("8859_1"),"JISAutoDetect"); 等の時に、paramを static final String にしたいのです。 自分でも文法が出来てないとは思いますが、よろしくお願いします。

    • ベストアンサー
    • Java
  • セッションを使ったint型の値の保持

    こんにちは。 少し文が長いですがよろしくお願いします。 AccessのDBから取得したint型の値を、セッションを使って保持したいのですが while(rs.next()){ String name = rs.getString("NAME"); int value = rs.getInt("VALUE"); HttpSession session1 = req.getSession(true); HttpSession session2 = req.getSession(true); session1.setAttribute("Name", name); session2.setAttribute("Value", value); dispatcher2.include(req, res); } のコードの session2.setAttribute("Value", value); でコンパイルエラー DBAccess.java [37:1] javax.servlet.ServletRequest の setAttribute(java.lang.String,java.lang.Object) は (java.lang.String,int) に適用できません。 がでてうまくいきません。 セッションを使ってint型の値の保持を行うにはどうすればよいのでしょうか?

    • ベストアンサー
    • Java
  • 初めての、Servlet→JSP

    今、DB検索Servletを開発しています。 そこで、コンパイル時のエラーについて、いきずまったので少し質問 させてください。 内容は、Servletで、コネクションをDBに接続し、検索。 JSPで表示といった、システムです。 public class goo extends HttpServlet { public void init() throws ServletException { /* DB接続処理 */ } public void doPost (HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException { try{ Statement statement = con.createStatement(); String query ="SELECT * FROM test"; ResultSet ResObj = statement.executeQuery(query); ResObj.close(); statement.close(); } catch(Exception ex){ ex.print.StackTrace(); } try{ req.setAttribute("ResObj",ResObj); getServletConfig(). getServletContext(). getRequestDispatcher("kekka.jsp"); forward(req,res); } catch(Exception ex){ ex.print.StackTrace(); } } } で、コンパイルのエラーが、 定義されてない変数、クラス、またはパッケージ名: ResObj req.setAttribute("ResObj",ResObj);                 ^ と、出ます。 定義とは、 ResultSet ResObj = statement.executeQuery(query); の内容ではないのですか? それとも、他で定義しないとダメなんですか? ご指摘、宜しくお願いします。

    • ベストアンサー
    • Java
  • beanの利用

    これは、ブラウザから、Parameterを受け取り、DBで検索内容を取得してくると言う、内容です。 一部省略しますが、下記に表示します。 /*GooServlet*/ public class KensakuServlet5 extends HttpServlet{ public void doPost (HttpServletRequest req,HttpServletResponse res) throws ServletException, IOException { dbAccess dbaccess = new dbAccess(); String id = req.getParameter("id"); dbaccess.setId(id); dbaccess.Execute(); req.setAttribute("dba",dbaccess); RequestDispatcherrd=sc.getRequestDispatcher ("/Hyouji.jsp"); rd.forward(req,res); /*dbAccess*/ public class dbAccesss { private String id = getId(); public void Execute(){ /*DB接続処理*/ while(resultset.next()){ id = resultset.getString("id"); } public void setId(String val){id = val;} public String getId(){return(id);} } /*Hyouji.jsp*/ <%@ page contentType="text/html;charset=Shift_JIS" %> <jsp:useBean id='dba'scope='request'class='dbAccess'/> <html> <body> <%=dba.getId()%> </body> </html> です。少し、省略しましたが・・。 で、今回の質問は、ファイルへの書き出しを加える事なのです。 ファイルへの書き出しは、下記のような流れです。 FileOutputStream fos = new FileOutputStream("c:\\inetpub\\hello.text"); OutputStreamWriter osw = new OutputStreamWriter(fos , "Shift_JIS"); BufferedWriter bw = new BufferedWriter(osw); bw.write(goo); } このような処理を、beanで取得した値(dba.getId())を、ファイルに書き出したいのです。 説明が下手ですみませんが、ご助言よろしくお願いします。

    • ベストアンサー
    • Java
  • サーブレット初歩に関して。

    package oty; import java.io.IOException; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; /** * Servlet implementation class Otys */ public class Otys extends HttpServlet { private static final long serialVersionUID = 1L; /** * @see HttpServlet#HttpServlet() */ public Otys() { super(); // TODO Auto-generated constructor stub } /** * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response) */ protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { // TODO Auto-generated method stub } /** * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response) */ protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { // TODO Auto-generated method stub } } 初期状態がこんな状態なんですが、これになにを追加したらhelloworldとでますか?? 普通にJAVA入門みたいに、System.out.printlnしたらいいんでしょうか??

    • ベストアンサー
    • Java
  • メソッドの引数に指定されているインタフェースについて

    最近サーブレットをいじっているので例としてサーブレットを扱いますが、一般的な話題として扱っていただければと存じます。 非常に質問を文章化しにくいのですが・・ たとえば、クラスHttpServletには以下のようなメソッドがあります。 doGet(HttpServletRequest req, HttpServletResponse resp) このメソッドの引数に指定されているHttpServletRequest/Responseはいずれもインタフェースなわけですが、メソッドの引数にインタフェースを指定するというのは、具体的にどういうことなのでしょうか? これがたとえばintだったりStringだったりした場合は簡単にイメージできるのですが、インタフェースだとさっぱりわかりません。 質問がわかりにくいかもしれませんが、よろしくお願いいたします。

    • ベストアンサー
    • Java
  • 画面遷移時のデータ遷移について

    文字数制限があったので短くして投稿させていただきます。 入力画面で入力した値を次の確認画面で表示したいと思っているんですがどのようにしたらよいでしょうか? web.xmlでは定義してあります。 入力前のJSPは作成しました。 入力後のJSPをどのようにしたらいいでしょうか? また入力画面のJSPは変更する必要があるでしょうか? --------------------------------------------- package monndai; import java.io.IOException; import javax.servlet.RequestDispatcher; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; public class Monsyo_NewFileDate extends HttpServlet { public void doPost(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException { RequestDispatcher reqDis = null; try { System.out.println(); //表示JSP決定 reqDis = req.getRequestDispatcher("/jsp/Monsyo_newFileDate.jsp"); //forward reqDis.forward(req,res); } catch (Exception e) { System.out.println("err"); e.printStackTrace(); req.setAttribute("exception", e); reqDis = req.getRequestDispatcher("/jsp/error.jsp"); reqDis.forward(req, res); } } } --------------------------------------------- package monndai; import java.io.IOException; import javax.servlet.RequestDispatcher; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; public class Monsyo_NewFileInputData extends HttpServlet { public void doPost(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException { RequestDispatcher reqDis = null; try { System.out.println(); //表示JSP決定 reqDis = req.getRequestDispatcher("/jsp/Monsyo_newFileInputData.jsp"); //forward reqDis.forward(req,res); } catch (Exception e) { System.out.println("err"); e.printStackTrace(); req.setAttribute("exception", e); reqDis = req.getRequestDispatcher("/jsp/error.jsp"); reqDis.forward(req, res); } } } --------------------------------------------- <%@page language="java" %> <%@page contentType="text/html;charset=EUC-JP"%> <% String returnPath0 = null; String returnPath1 = null; %> <html> <head> <script language="JavaScript"> <!--//  function checkLength(obj, maxlen) {   if(obj.value.length > maxlen) {    obj.disabled = true;    obj.value = obj.value.substring(0,maxlen);   }   obj.disabled = false;   obj.focus(); // BackSpace防止  } function sendRequest(path) { document.fr.action = path; document.fr.submit(); } --> </script> </head> <title>新問処発行</title> <body> <form name="fr" onSubmit="true" method="POST" > <div align="left"> <h3> 新問処発行</h3> <br> <日付> (XXXX/XX/XX)<br> <input type="text" align="left" maxlength="10" name=" " size="15" > <br> <タイトル>(100文字以内)<br> <textarea rows="5" cols="60" name="title" onkeyup="checkLength(this, 100);" style="ime-mode:active"></TEXTAREA> <br> <% returnPath0 = "sendRequest('/mondai/Monsyo_NewFileInputDataServlet')"; returnPath1 = "sendRequest('/mondai/Monsyo_ToppageServlet')"; %> <br> <input type="button" value="入力" onClick="<%= returnPath0 %>"/> <input type="button" value="戻る" onClick="<%= returnPath1 %>"/> </div> </form> </body> </html> ---------------------------------------------

  • 画面遷移時のデータ遷移について

    Javaにも記載してしまったのですがこちらに記載すべきかと思い投稿させていただきました。 2重投稿になってしまうため削除しようとしたのですが24時間経たないと削除できませんでした。 24時間後に1つにしようと思います。 皆様のお力をお貸しください。 よろしくお願いします。 入力画面で入力した値を次の確認画面で表示したいと思っているんですがどのようにしたらよいでしょうか? web.xmlでは定義してあります。 入力前のJSPは作成しました。 入力後のJSPをどのようにしたらいいでしょうか? また入力画面のJSPは変更する必要があるでしょうか? --------------------------------------------- package monndai; import java.io.IOException; import javax.servlet.RequestDispatcher; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; public class Monsyo_NewFileDate extends HttpServlet { public void doPost(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException { RequestDispatcher reqDis = null; try { System.out.println(); //表示JSP決定 reqDis = req.getRequestDispatcher("/jsp/Monsyo_newFileDate.jsp"); //forward reqDis.forward(req,res); } catch (Exception e) { System.out.println("err"); e.printStackTrace(); req.setAttribute("exception", e); reqDis = req.getRequestDispatcher("/jsp/error.jsp"); reqDis.forward(req, res); } } } --------------------------------------------- package monndai; import java.io.IOException; import javax.servlet.RequestDispatcher; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; public class Monsyo_NewFileInputData extends HttpServlet { public void doPost(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException { RequestDispatcher reqDis = null; try { System.out.println(); //表示JSP決定 reqDis = req.getRequestDispatcher("/jsp/Monsyo_newFileInputData.jsp"); //forward reqDis.forward(req,res); } catch (Exception e) { System.out.println("err"); e.printStackTrace(); req.setAttribute("exception", e); reqDis = req.getRequestDispatcher("/jsp/error.jsp"); reqDis.forward(req, res); } } } --------------------------------------------- <%@page language="java" %> <%@page contentType="text/html;charset=EUC-JP"%> <% String returnPath0 = null; String returnPath1 = null; %> <html> <head> <script language="JavaScript"> <!--//  function checkLength(obj, maxlen) {   if(obj.value.length > maxlen) {    obj.disabled = true;    obj.value = obj.value.substring(0,maxlen);   }   obj.disabled = false;   obj.focus(); // BackSpace防止  } function sendRequest(path) { document.fr.action = path; document.fr.submit(); } --> </script> </head> <title>新問処発行</title> <body> <form name="fr" onSubmit="true" method="POST" > <div align="left"> <h3> 新問処発行</h3> <br> <日付> (XXXX/XX/XX)<br> <input type="text" align="left" maxlength="10" name=" " size="15" > <br> <タイトル>(100文字以内)<br> <textarea rows="5" cols="60" name="title" onkeyup="checkLength(this, 100);" style="ime-mode:active"></TEXTAREA> <br> <% returnPath0 = "sendRequest('/mondai/Monsyo_NewFileInputDataServlet')"; returnPath1 = "sendRequest('/mondai/Monsyo_ToppageServlet')"; %> <br> <input type="button" value="入力" onClick="<%= returnPath0 %>"/> <input type="button" value="戻る" onClick="<%= returnPath1 %>"/> </div> </form> </body> </html> ---------------------------------------------

  • type 4 jdbc経由のDB2へのアクセスでNo suitable driverエラー

    type 2 jdbcドライバを使ったDB2へアクセス失敗して困っております。 -db2jcc.jar db2jcc_licence_cu.jar db2jcc_licence_cisuz.jar をクラスパスに指定。 public class sampleAction extends Action { public ActionForward execute( ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws Exception { ServletContext context = getServlet().getServletContext(); sampleForm sap = new sampleForm(); String ID = sap.getId(); String PW = sap.getPw(); try { Class.forName("com.ibm.db2.jcc.DB2Driver ").newInstance(); Connection dbConn = DriverManager.getConnection("jdbc:db2:MYMALL", "db2admin", "db2admin"); Statement stmt = dbConn.createStatement(); ResultSet rs =stmt.executeQuery("select * from DB2ADMIN.PASSWORD where ID = '" + ID + "'"); String pwstr = rs.getString("PW"); if (PW.equals(pwstr)) { String namestr = rs.getString("NAME"); sap.setNameresult(namestr); String name1 = sap.getNameresult(); context.setAttribute("NAME1", name1); } stmt.close(); dbConn.close(); } catch (Exception e) { e.printStackTrace(); } return (mapping.findForward("success")); } } 上記のコードを実行すると java.lang.ClassNotFoundException: com/ibm/db2/jcc/DB2Driver となります。 チェックするべき点や 解決策についてご存知の方がいらっしゃいましたら どうか宜しくお願いします。

    • ベストアンサー
    • Java
  • JSPでのArrayListの表示について困っています

    以下のようにしてスレッドNoが同じものだけ表示したいと考えております。 servletの「text」という変数にはすべての値が格納されているところまでは確認できました。 それをJSPにて表示したいのですが、どのようにすれば出力されるのかわかりません。 どなたかお教えいただければと思います。 宜しく御願い致します。 --------------------------------------------------------- java /** * *TEXTテーブルからスレッドNoが同じものを返すメソッド * * */ public ArrayList selecttext(int no)throws SQLException{ ArrayList<Textbeen> list = new ArrayList<Textbeen>(); TextDAO kei =new TextDAO(); Connection db=kei.createConnection(); Statement sttSql=db.createStatement(); ResultSet rs=sttSql.executeQuery("SELECT * FROM TEXT WHERE KB_TH_NO='"+no+"' "); while(rs.next()){ String name=rs.getString("KB_NAME"); String tino =rs.getString("KB_TITLE_NO"); String title = rs.getString("KB_TITLE"); String mail = rs.getString("KB_MAIL"); String text = rs.getString("KB_TEXT"); String pass = rs.getString("KB_TITLE_PASS"); String date = rs.getString("KB_TIME"); int th_no = rs.getInt("KB_TH_NO"); Textbeen thread = new Textbeen(name, title, tino, mail, text, pass, date, th_no); //TO(Threadオブジェクト)を、保持するリストに追加 list.add(thread); } kei.closeConnection(db); return list; } ---------------------------------------------------------- servlet ArrayList text = new ArrayList(); try{ text = list.selecttext(TH_no); } catch(Exception e){ e.getStackTrace(); } request.setAttribute("test", text); String nextPage = "/view/user/ThreadTop.jsp"; ----------------------------------------------------------