日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

Servlet第三篇【request和response简介、response的常见应用】

發布時間:2025/3/12 编程问答 19 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Servlet第三篇【request和response简介、response的常见应用】 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

response、request對象

Tomcat收到客戶端的http請求,會針對每一次請求,分別創建一個代表請求的request對象、和代表響應的response對象

既然request對象代表http請求,那么我們獲取瀏覽器提交過來的數據,找request對象即可。response對象代表http響應,那么我們向瀏覽器輸出數據,找response對象即可。

什么是HttpServletResponse對象?

http響應由狀態行、實體內容、消息頭、一個空行組成。HttpServletResponse對象就封裝了http響應的信息。

HttpServletResponse的應用

調用getOutputStream()方法向瀏覽器輸出數據

調用getOutputStream()方法向瀏覽器輸出數據,getOutputStream()方法可以使用print()也可以使用write(),它們有什么區別呢?我們試驗一下。代碼如下

//獲取到OutputStream流ServletOutputStream servletOutputStream = response.getOutputStream();//向瀏覽器輸出數據servletOutputStream.print("aaaa");

成功輸出,好像沒什么毛病。

我們試著輸出中文試試

//獲取到OutputStream流ServletOutputStream servletOutputStream = response.getOutputStream();//向瀏覽器輸出數據servletOutputStream.print("中國!");

出異常了!!!

為什么會出現異常呢?在io中我們學過,outputStream是輸出二進制數據的,print()方法接收了一個字符串,print()方法要把“中國”改成二進制數據,Tomcat使用IOS 8859-1編碼對其進行轉換,“中國”根本對ISO 8859-1編碼不支持。所以出現了異常

我們再看看write()方法,先向瀏覽器輸出英文數據

response.getOutputStream().write("aaa".getBytes());

沒有問題

再試試輸出中文數據

response.getOutputStream().write("你好呀我是中國".getBytes());

貌似也沒有問題。


為什么使用write()方法能夠正常向瀏覽器輸出中文呢?“你好呀我是中國”.getBytes()這句代碼在轉成byte[]數組的時候默認查的是gb2312編碼,而"你好呀我是中國"支持gb2312編碼,所以可以正常顯示出來。

但是,程序要實現通用性,應該使用的是UTF-8編碼,我們在字符串轉換成字節數組時指定UTF-8編碼,看看會怎么樣。

response.getOutputStream().write("你好呀我是中國".getBytes("UTF-8"));

好的,成功把它搞成亂碼了!!!

為什么它變成了亂碼呢?原因是這樣的:我在向服務器輸出的中文是UTF-8編碼的,而瀏覽器采用的是GBK,GBK想顯示UTF-8的中文數據,不亂碼才怪呢!

既然如此,我將瀏覽器的編碼改成UTF-8試試。

亂碼問題又解決了。可是,每次編寫UTF-8程序時都要去網頁上改編碼格式嗎?這樣明顯不可能的。

既然HTTP響應有對瀏覽器說明回送數據是什么類型的消息頭,那么HttpServletResponse對象就應該有相對應的方法告訴瀏覽器回送的數據編碼格式是什么

于是乎就去查找Servlet API,找到了設置消息頭的方法

//設置頭信息,告訴瀏覽器我回送的數據編碼是utf-8的response.setHeader("Content-Type", "text/html;charset=UTF-8");response.getOutputStream().write("你好呀我是中國".getBytes("UTF-8"));

瀏覽器在顯示數據時,自動把頁面的編碼格式置換成UTF-8,亂碼問題也解決了

另外,除了使用HttpServletResponse對象設置消息頭的方法,我可以使用html的標簽模擬一個http消息頭

下面是代碼:

//獲取到servletOutputStream對象ServletOutputStream servletOutputStream = response.getOutputStream();//使用meta標簽模擬http消息頭,告訴瀏覽器回送數據的編碼和格式servletOutputStream.write("<meta http-equiv='content-type' content='text/html;charset=UTF-8'>".getBytes());servletOutputStream.write("我是中國".getBytes("UTF-8"));

亂碼問題也可以解決

調用getWriter()方法向瀏覽器輸出數據

對于getWriter()方法而言,是Writer的子類,那么只能向瀏覽器輸出字符數據,不能輸出二進制數據

使用getWriter()方法輸出中文數據,代碼如下:

//獲取到printWriter對象PrintWriter printWriter = response.getWriter();printWriter.write("看完博客點贊!");

喜聞可見的事又出現了,我又出現亂碼了。

為什么出現亂碼了呢?由于Tomcat是外國人的寫,Tomcat默認的編碼是ISO 8859-1,當我們輸出中文數據的時候,Tomcat會依據ISO 8859-1碼表給我們的數據編碼,中文不支持這個碼表呀,所以出現了亂碼

既然如此,我設置一下編碼不就好了嗎,代碼如下:

//原本是ISO 8859-1的編碼,我設置成UTF-8response.setCharacterEncoding("UTF-8");//獲取到printWriter對象PrintWriter printWriter = response.getWriter();printWriter.write("看完博客點贊!");

我再訪問了一下,我的天!看起來更亂了!

為什么亂碼問題還沒有解決?細心的朋友會發現,我只是在中文轉換的時候把碼表設置成UTF-8,但是瀏覽器未必是使用UTF-8碼表來顯示數據的呀

好的,我們來看看瀏覽器的編碼格式,果然,瀏覽器使用GB2312顯示UTF-8的數據,不亂碼才怪呢

這個問題我們在上面已經是有兩種方法解決了【使用標簽模擬消息頭、設置消息頭】,Servlet還提供了一個方法給我們

//設置瀏覽器用UTF-8編碼顯示數據response.setContentType("text/html;charset=UTF-8");

好的,我們再來訪問一下

既然Servlet有那么多方法解決亂碼問題,是不是有一種是最簡便的呢?沒錯!下面這個方法是最簡便的,它不僅設置瀏覽器用UTF-8顯示數據,內部還把中文轉碼的碼表設置成UTF-8了,也就是說,response.setContentType(“text/html;charset=UTF-8”);把response.setCharacterEncoding(“UTF-8”)的事情也干了!

使用getWriter()顯示中文數據,只需要一個方法就搞掂了!

//設置瀏覽器用UTF-8編碼顯示數據,response.setContentType("text/html;charset=UTF-8");//獲取到printWriter對象PrintWriter printWriter = response.getWriter();printWriter.write("看完博客點贊!");

實現文件下載

下載資源我們在日常中也很常用,它是怎么做到的呢?要能夠給別人下載,服務器就應該有這個資源

現在我web站點下有一個圖片了!

既然瀏覽器發送所有的請求都是去找Servlet的話,那么我就寫一個Servlet,當別人訪問我這個Servlet的時候,它們就可以下載我這個圖片了!

java的文件上傳下載都是通過io流來完成的,既然要下載圖片,首先要能夠讀取到它

//獲取到資源的路徑String path = this.getServletContext().getRealPath("/download/1.png");//讀取資源FileInputStream fileInputStream = new FileInputStream(path);//獲取到文件名,路徑在電腦上保存是\\形式的。String fileName = path.substring(path.lastIndexOf("\\") + 1);

告訴瀏覽器,我要下載這個文件

//設置消息頭,告訴瀏覽器,我要下載1.png這個圖片response.setHeader("Content-Disposition", "attachment; filename="+fileName);

將讀取到的內容回送給瀏覽器

//把讀取到的資源寫給瀏覽器int len = 0;byte[] bytes = new byte[1024];ServletOutputStream servletOutputStream = response.getOutputStream();while ((len = fileInputStream.read(bytes)) > 0) {servletOutputStream.write(bytes, 0, len);}//關閉資源servletOutputStream.close();fileInputStream.close();

當我訪問時,瀏覽器就提示下載了。


也可以成功打開!

現在問題又有了,如果我文件的名字是中文呢?

我們再訪問一下,發現名字亂碼了(怎么都是亂碼)

為了解決文件名亂碼,我們要進行URL編碼,代碼如下:

response.setHeader("Content-Disposition", "attachment; filename=" + URLEncoder.encode(fileName, "UTF-8"));

再次訪問時,文件名亂碼問題就解決了!

實現自動刷新

以規定的時間讓頁面刷新,更新資源

讓瀏覽器實現自動刷新,那肯定又是修改消息頭了。

//每3秒自動刷新網頁一次response.setHeader("Refresh", "3");

為了更好的看效果,我們加入時間值進去

response.getWriter().write("time is :" + System.currentTimeMillis());

每三秒時間值就會發生變化

學完上面的,好像沒有什么用,自己上網的時候誰看得見這樣的東西。自動刷新,能夠實現頁面的跳轉】

我們登陸完網站,很多時候都會看見【登陸成功,3秒后自動跳轉…】,其實這個就是用Refresh來完成的。

response.setContentType("text/html;charset=UTF-8");response.getWriter().write("3秒后跳轉頁面.....");//三秒后跳轉到index.jsp頁面去,web應用的映射路徑我設置成/,url沒有寫上應用名response.setHeader("Refresh", "3;url='/index.jsp'");

看下效果

設置緩存

瀏覽器本身就存在著緩存機制

當我第一次訪問index.jsp時,瀏覽器向服務器發了兩次請求【一個是網頁的,一個是圖片的】

當我第二次訪問index.jsp的時候,瀏覽器將圖片緩存起來了!圖片不是重新加載的,是從緩存里面取出來的。

像股票類型的網頁是不能取緩存的數據的,數據都是要不斷更新的。下面我就禁止緩存的功能

//瀏覽器有三消息頭設置緩存,為了兼容性!將三個消息頭都設置了response.setDateHeader("Expires", -1);response.setHeader("Cache-Control","no-cache");response.setHeader("Pragma", "no-cache");//這里為了看效果PrintWriter printWriter = response.getWriter();printWriter.print("你好啊" + new Date().toString());

當然了,如果頁面有些數據不長期更新,你就將它設置成緩存,這樣可以提高服務器的性能

實現數據壓縮

網頁上的信息量是很大的,如果不將數據壓縮再回送給瀏覽器,這樣就十分耗費流量

現在我有一篇文章要輸出給瀏覽器

response.setContentType("text/html;charset=UTF-8");String ss = "fsdfhsdfhuisdhfusdhfuids" +"fsdfdsfsdfsdfdsfdafdsfhsdjfhsdjkfhkjds" +"fdsfjdslkfjsldkfjsdlkfjsdkfsdjkff" +"fsjdfjdsklfjdsklfjkldsfjlksdjflksdjflkds" +"dsjfklsdjflsdjfkldsfkjsdkfjsldkfjsdlfk" +"fdsjlkfjdslkfjsdlkfjlkasjflk";response.getWriter().write("原來的長度是:"+ss.getBytes().length+"</br>");//輸出給瀏覽器response.getWriter().write(ss);

訪問一下可以看到,原來的長度是201

壓縮的原理是什么?我們知道getOutputStream()和getWriter()都是直接把數據輸出給瀏覽器的。現在我要做的就是讓數據不直接輸出給瀏覽器,先讓我壓縮了,再輸出給瀏覽器。java提供了GZIP壓縮類給我們

就讓我們使用GZIP類來對數據壓縮吧

//GZIP的構造方法需要一個OutputStream子類對象,究竟哪個對象適合,我們看下write()方法GZIPOutputStream gzipOutputStream = new GZIPOutputStream();//查看了下API,write()接收的是byte[]類型的。gzipOutputStream.write();

于是我就在構造函數上傳遞個ByteArrayOutputStream給它

//既然是byte[]類型,那么我就給他一個ByteArrayOutputStreamGZIPOutputStream gzipOutputStream = new GZIPOutputStream(new ByteArrayOutputStream());

而用GZIPOutputStream寫數據的時候,是把數據寫到ByteArrayOutputStream上的,等會還要把數據取出來,再寫給瀏覽器,于是就不能以匿名內部類的方式給GZIPOutputStream,必須把ByteArrayOutputStream定義出來,

//創建GZIPOutputStream對象,給予它ByteArrayOutputStreamByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();GZIPOutputStream gzipOutputStream = new GZIPOutputStream(byteArrayOutputStream);//GZIP對數據壓縮,GZIP寫入的數據是保存在byteArrayOutputStream上的gzipOutputStream.write(ss.getBytes());//gzipOutputStream有緩沖,把緩沖清了,并順便關閉流gzipOutputStream.close();

把壓縮后的數據取出來,寫給瀏覽器

//將壓縮的數據取出來byte[] bytes = byteArrayOutputStream.toByteArray();//將壓縮的數據寫給瀏覽器response.getOutputStream().write(bytes);

我們來對比一下壓縮前的大小和壓縮后的大小

數據的確是壓縮了,然而,為什么又亂碼了啊?很簡單,既然你壓縮了數據,你寫給瀏覽器,瀏覽器是不知道你這是壓縮后的數據,它是以正常的方式打開數據的。這當然造成亂碼啦!,現在我要告訴瀏覽器我這是壓縮數據

//告訴瀏覽器這是gzip壓縮的數據response.setHeader("Content-Encoding","gzip");//再將壓縮的數據寫給瀏覽器response.getOutputStream().write(bytes);

再次訪問一下

生出隨機圖片

生成隨機圖片這是非常常見的。在我們登陸的時候經常要寫驗證碼,而那些驗證碼是一張圖片,就是通過HttpServletResponse寫給瀏覽器的。

要生成一張圖片,java提供了BufferedImage類供我們使用

//在內存中生成一張圖片,寬為80,高為20,類型是RGBBufferedImage bufferedImage = new BufferedImage(80, 20, BufferedImage.TYPE_INT_RGB);//獲取到這張圖片Graphics graphics = bufferedImage.getGraphics();//往圖片設置顏色和字體graphics.setColor(Color.BLUE);graphics.setFont(new Font(null, Font.BOLD, 20));//往圖片上寫數據,先寫個12345,橫坐標是0,縱坐標是20【高度】graphics.drawString("12345", 0, 20);

好的,現在我們在內存中創建了一張圖片,并寫上了12345。接著,我們要把圖片寫給瀏覽器了。把圖片寫給瀏覽器,java又提供了圖片流【ImageIO】給我們使用

//要往瀏覽器寫一張圖片,那要告訴瀏覽器回送的類型是一張圖片response.setHeader("ContentType", "jpeg");//java提供了圖片流給我們使用,這是一個工具類//把圖片傳進去,類型是jpg,寫給瀏覽器ImageIO.write(bufferedImage, "jpg", response.getOutputStream());

我們來訪問一下,看下圖片長什么樣

這樣太丑了,我們把背景改成白色看看

//把白色填充整張圖片graphics.setColor(Color.white);graphics.fillRect(0, 0, 80, 20);

再看看效果,這明顯好看多了

好的,我們的圖片數字不可能是人工寫的,數字應該是隨機產生的!這個就簡單了。現在我要生成7位的隨機數,生成隨機數的方法如下

private String makeNum() {Random random = new Random();//這樣就會生成0-7位的隨機數,現在問題又來了,如果隨機數不夠7位呢?如果不夠7位,我們加到7位就行了int anInt = random.nextInt(9999999);//將數字轉成是字符串String num = String.valueOf(anInt);//判斷位數有多少個,不夠就加StringBuffer stringBuffer = new StringBuffer();for (int i = 0; i < 7 - num.length(); i++) {stringBuffer.append("0");}return stringBuffer.append(num).toString();}

如果要生成中文,就找中文映射表即可。

重定向跳轉

什么是重定向跳轉呢?點擊一個超鏈接,通知瀏覽器跳轉到另外的一個頁面就叫重定向跳轉。是通知瀏覽器去跳轉,這很重要。頁面之間的跳轉有兩種方式:重定向和轉發,至于什么時候用重定向,什么用轉發,我在講完HttpServletRequest對象的時候會詳細說明。

我們來使用以下HttpServletResponse對象的重定向

//重定向到index.jsp頁面response.sendRedirect("/zhongfucheng/index.jsp");

在瀏覽器的地址欄訪問Servlet222

跳轉到index.jsp頁面,地址欄發生了變化

我們再來看看http協議發生了什么

從圖上看,我們看到了兩個狀態碼,一個是302。一個是200。302狀態碼在http協議中代表的是臨時重定向。舉個例子:我找紀律委員說:給我一份請假表,我要回家。紀律委員告訴我:我這里沒有請假表,你去找輔導員吧。再看回我訪問Sevlet222時:我找Servlet222,Servlet222告訴瀏覽器:我沒有你想要的資源,你要的資源在index.jsp頁面中,你自己去找吧。

很容易看出重定向是通過302狀態碼和跳轉地址實現的。于是乎,我們設置http消息頭就可以實現重定向跳轉

//設置狀態碼是302response.setStatus(302);//HttpServletResponse把常用的狀態碼封裝成靜態常量了,所以我們可以使用SC_MOVED_TEMPORARILY代表著302response.setStatus(HttpServletResponse.SC_MOVED_TEMPORARILY);//跳轉的地址是index.jsp頁面response.setHeader("Location", "/zhongfucheng/index.jsp");

其實sendRedirect()方法就是對setStatus()和setHeader()進行封裝,原理就是setStatus()和setHeader()

getWriter和getOutputStream細節

  • getWriter()和getOutputStream()兩個方法不能同時調用。如果同時調用就會出現異常
  • Servlet程序向ServletOutputStream或PrintWriter對象中寫入的數據將被Servlet引擎從response里面獲取,Servlet引擎將這些數據當作響應消息的正文,然后再與響應狀態行和各響應頭組合后輸出到客戶端。
  • Servlet的serice()方法結束后【也就是doPost()或者doGet()結束后】,Servlet引擎將檢查getWriter或getOutputStream方法返回的輸出流對象是否已經調用過close方法,如果沒有,Servlet引擎將調用close方法關閉該輸出流對象.
  • 創作挑戰賽新人創作獎勵來咯,堅持創作打卡瓜分現金大獎

    總結

    以上是生活随笔為你收集整理的Servlet第三篇【request和response简介、response的常见应用】的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

    主站蜘蛛池模板: 亚洲痴女 | 欧美日韩中文一区 | www.精品| 欧美高清在线观看 | 91网入口| 在线播放小视频 | 亚洲人成色777777精品音频 | 国产av 一区二区三区 | 午夜视频免费在线观看 | japanese24hdxxxx中文字幕 | 日本成人久久 | 97视频免费 | 久久久综合久久 | 亚州成人| sm调教羞耻姿势图片 | 国产最新自拍 | 中文字幕在线观看视频www | 亚洲精品日韩av | 被黑人猛躁10次高潮视频 | 天天色天天射天天干 | 韩国视频一区二区 | 色男人影院 | 激情国产一区 | av鲁丝一区鲁丝二区鲁丝三区 | 久久露脸国语精品国产 | 亚洲一区二区视频在线 | 欧美精品videos另类 | 在线观看免费av片 | 美女色网站| 欧美成人女星 | 神马伦理影视 | 最新中文字幕第一页 | 亚洲一本在线 | 国产在线观看中文字幕 | 精品人伦一区二区三区 | 老熟妇高潮一区二区高清视频 | 99热免费 | 综合色av | 日本少妇aaa| 色婷婷色 | 黄色av软件 | 自拍毛片 | 日韩欧美精品一区二区 | 搡老熟女国产 | 北岛玲在线 | 俄罗斯videodesxo极品 | 粗暴video蹂躏hd | 在线伊人| 久久久久久久无码 | 午夜影院美女 | 91在线无精精品一区二区 | 神秘电影永久入口 | 日韩欧美国产精品 | 男生脱女生衣服 | 高h大肚孕期孕妇play | 亚洲天堂网一区 | 精品人妻一区二区三区久久夜夜嗨 | 亚洲一区小说 | av少妇| 蜜臀久久精品 | 日本美女视频一区 | 色综合天天综合综合国产 | 国产日日干 | 天天插插插 | 中文字幕第一区综合 | 久久综合婷婷 | 九九热在线视频 | 变态另类丨国产精品 | 隔壁人妻偷人bd中字 | 亚洲精品乱码久久久久久麻豆不卡 | 国产高清视频在线播放 | 欧美日韩一区二区三区四区 | 九九热精品在线视频 | www.sesehu| 国产伦精品一区二区三区精品 | 日本三级日本三级日本三级极 | 久久99精品视频 | 97香蕉| 在线观看的av网站 | 欧美精品二区 | 国内自拍第一页 | 欧美日韩五月天 | 久久久www成人免费毛片 | 黄色成人在线播放 | 久久综合第一页 | 最新成人| 亚洲第九页 | 久操福利视频 | 亚洲美女屁股眼交8 | 久久合| 草草视频网站 | 一区二区三区久久久 | 涩涩在线看 | 亚欧洲精品视频 | 欧美一区二区三区免费视频 | 亚州综合 | 日本欧美在线视频 | 色婷亚洲 | 日本一区二区三区在线免费观看 |