精通Java學習之路(四)

来源:https://www.cnblogs.com/hepingan/archive/2023/08/24/17653169.html
-Advertisement-
Play Games

—併發包— 大型企業開發才用,我Java學得差不多以後再來學,主要是有點難,沒學泛型與集合… 練手的ConcurrentHashMap: import java.util.HashMap;import java.util.Hashtable;import java.util.concurrent.C ...


—併發包—

大型企業開發才用,我Java學得差不多以後再來學,主要是有點難,沒學泛型與集合…

練手的ConcurrentHashMap:

import java.util.HashMap;
import java.util.Hashtable;
import java.util.concurrent.ConcurrentHashMap;

public class bingfa {
public static HashMap<String,String> maps=new HashMap<>();
// public static Map<String,String> maps=new Hashtable<>();

public static void main(String[] args) {
Runnable r1=new MyRunnable();
Thread t1=new Thread(r1,"線程1");
Thread t2=new Thread(r1,"線程2");

t1.start();
t2.start();
try {
t1.join();//讓t1跑完,主線程不能競爭t1的CPU
t2.join();//讓t2跑完,主線程不能競爭t2的CPU
} catch (InterruptedException e) {
throw new RuntimeException(e);
}System.out.println("元素個數:"+maps.size());
}
static class MyRunnable implements Runnable{
@Override
public void run() {
for(int i=1;i<=500000;i++){
bingfa.maps.put(Thread.currentThread().getName()+i,Thread.currentThread().getName()+i);
}
}}
}

—Map集合—

Map集合特點:無序性,不重覆性(後面重覆的鍵對應的元素會覆蓋前面的整個元素),無索引的,對值無要求都可以為null。一個元素的組成為鍵和值,一個鍵對應一個值,就像地圖上一個地方對應一個地點名字,所以叫Map集合。

HashMap:無序,不重覆,無索引,值不做要求。經典的用得最多。

LinkedHashMap:有序,不重覆,無索引,值不做要求。

TreeMap:浮點型的大小比較按照自己的排序,不重覆,無索引,值不做要求。

Map的創建:Map<引用數據類型,引用數據類型> map=new HashMap/LinkedHashMap/TreeMap<>();ps:引用數據類型可以是其他類名的哦~

添加數據:map.put(xx,xx);

刪除特定元素:map.remove(鍵);刪除全部元素就直接map.clear();

判斷是否包含某個鍵:map.containsKey(鍵);

判斷是否包含某個值:map.containsValue(值);

將maps2的所有元素全部仍到maps中:map.putAll(maps2);

獲取對應鍵的值:map.get(鍵);

Set<String> keys=map.keySet();//獲取全部鍵的集合,Set無序不重覆
for (String key: keys){
System.out.println(key);
}
Collection<Integer> values=map.values();//因為值可能有重覆,所以用Collection集合
for (Integer value: values){
System.out.println(value+”,”+map.size());
}

遍歷方法:

遍歷方式1:鍵找值(key的值為String,value的類型為Integer):for(String key:maps.keySet()){Integer value =maps.get(key);System.out.println(key+”=”+value)};

遍歷方式2:鍵值對方式獲取:相較於鍵找值更加面向對象,但代碼複雜,它是把鍵值對當成一個整體遍歷,也就是直接使用foreac遍歷:for(被遍歷集合的元素類型 變數 :集合名稱){…};有點像python的字典,創建方法:Set<Map.Entry<String,Integer>> xxx=maps.entrySet();

遍歷方式3(最簡單的):k,v只是個隨便定義的變數,名字亂取都行

maps.forEach((k,v) ->{
System.out.println(k+”–>”+v);
});

—-網路通信—-

C/S結構的軟體開發:客戶需要下載客戶端,一更新客戶端也要更新。
B/S結構軟體開發:類似於網上開發,客服不用下客服端。
網路通信三要素:協議,IP地址,埠號。
協議就是電腦網路客戶端與服務端通信必須事先約定和彼此遵守的通信規則,一般有HTTP,FTP,TCP,UDP,SSH,SMTP.
IP地址:Internet Protocol Address互聯網協議地址。有IPv4和IPv6.

IPv4:4個位元組,32位組成
埠:如果說IP相當於一個酒店,埠就相當於酒店的房間號。埠取值範圍:0~65535.比如瀏覽器的埠號就是80。
查看自己的ip:在cmd命令板輸入ipconfig,嘗試連接:ping ip地址或網站功能變數名稱。
獲取本地地址對象:(如果是公網IP就會優先輸出公網IP,沒有就是本地IP)
Inet4Address ip = (Inet4Address) Inet4Address.getLocalHost();
        System.out.println(ip.getHostName());
        System.out.println(ip.getHostAddress());
獲取網站的ip地址:InetAddress ip2=InetAddress.getByName(“www.hepingan.top”);
        System.out.println(ip2.getHostName());
        System.out.println(ip2.getHostAddress());
測試連接:InetAddress ip3=InetAddress.getByName(“www.baidu.com”);
        System.out.println(ip3.isReachable(5000));//ping
相當於ping xxx,在規定時間內連接,成功輸出true,失敗false

UDP通信:

與服務端傳輸信息不需要進行交手,所以不怎麼安全,但可以用作開發實時通訊等。
創建集裝箱的參數:DatagramPacket packet =new DatagramPacket(數據包,數據包的長度,【IP地址】,【埠號】);發送的客戶端要寫【】內的,接受的服務端不用寫。
創建接收和發送數據的碼頭:DataSocket socket =new DataSocket();
(客戶端)發送數據:socket.send(packet);
(服務端)接收數據:socket.receive(packet);
關閉碼頭:socket.close();

TCP通信(重點):

一般web網站都是用的TCP/IP協議。
TCP/IP協議 ==> Transfer Control Protocol ==> 傳輸控制協議
TCP/IP協議的特點
* 面向連接的協議
* 只能由客戶端主動發送數據給伺服器端,伺服器端接收到數據之後,可以給客戶端響應數據。
* 通過三次握手建立連接,連接成功形成數據傳輸通道。
* 通過四次揮手斷開連接
* 基於IO流進行數據傳輸
* 傳輸數據大小沒有限制
* 因為面向連接的協議,速度慢,但是是可靠的協議。

客戶端的開發流程:
1.客戶端要請求於服務端的socket管道連接。
2.從socket通信管道中得到一個位元組輸出流
3.通過位元組輸出流給服務端寫出數據。
服務端的開發流程:
1.註冊埠。
2.接收客戶端的Socket管道連接。
3.從socket通信管道中得到一個位元組輸入流。
4.從位元組輸入流中讀取客戶端發來的數據。
小結:
1.客戶端用Socket連接服務端。Socket socket=new Socket(ip,port)
2.服務端用ServerSocket註冊埠,接收客戶端的Socket連接。ServerSocket ss=new ServerSocket(port);
3.通信是很嚴格的,對方怎麼發,你就應該怎麼收,對方發多少你就只能收多少。
4.實現的面向連接的socket端到端的通信管道,一方如果出現對象,另一方會出現異常!

2023最新IO傳輸方法:使用DataI/OStream數據輸入輸出流進行傳輸,對DataStream對象使用writeUTF和readUTF進行就收發送和讀寫。就不用用byte了

總的方法就是客戶端先創建Socket管道用於數據的傳輸管道,需要輸入傳輸的IP地址和埠,再創建OutputStream對象從Socket管道中得到一個位元組輸出流,然後用DataOutputStream包裝成高級的數據輸出流,最後用writeUTF(msg)就可以發送消息了。服務端先註冊一個埠號:ServerSocket ss=new ServerSocket(埠號),然後等待連接管道Socket socket =ss.accept(),再創建InputStream並使用DataInputStream打包成數據輸入流,最後創建個String類型變數使用readUTF()讀寫數據就行了。

volatile類型變數用於解決多個線程訪問共用變數是會出現一個線程修改變數值後其他線程看不到最新的線程值。

TCP通信實現多個客服端和服務端發消息(未使用線程池的):學完網路通信能寫出下麵的就可以畢業了~

客戶端:

package new_TCPstudy;

import java.io.DataOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.net.InetAddress;
import java.net.Socket;
import java.net.UnknownHostException;
import java.util.Scanner;

public class Client {
public static void main(String[] args) throws IOException {
System.out.println("客服端啟動");
Socket socket=new Socket(InetAddress.getLocalHost(),9999);
//從socket管道中得到一個位元組輸出流
OutputStream OutputStream=socket.getOutputStream();
//包裝成高級的數據輸出流
DataOutputStream dataOutputStream=new DataOutputStream(OutputStream);
Scanner scanner=new Scanner(System.in);
while (true){
System.out.println("請說:");
String msg=scanner.nextLine();
//輸入exit退出客戶端
if("exit".equals(msg)){
System.out.println("退出客服端...");
dataOutputStream.close();
socket.close();
break;
}
dataOutputStream.writeUTF(msg);
dataOutputStream.flush();
}
}
}

服務端:

package new_TCPstudy;

import java.io.*;
import java.net.ServerSocket;
import java.net.Socket;

public class Server {
public static void main(String[] args) throws IOException {
System.out.println("服務端,啟動!");
//為服務端註冊埠
ServerSocket ss=new ServerSocket(9999);
//創建管道等待接收連接
while (true){
Socket socket=ss.accept();
System.out.println(socket.getInputStream()+"上線了~");
new ServerThread(socket).start();
}
}
public static class ServerThread extends Thread{
private Socket socket;
public ServerThread(Socket socket){
this.socket=socket;
}
@Override
public void run() {
try {
InputStream inputStream=socket.getInputStream();
//包裝成高級的數據輸入流
DataInputStream dataInputStream=new DataInputStream(inputStream);
while (true){
String msg=dataInputStream.readUTF();
System.out.println("收到來自"+socket.getRemoteSocketAddress()+"的消息:"+msg);
}
}catch (Exception e){
System.out.println(socket.getRemoteSocketAddress()+"下線了");
}
}
}
}

Map集合學習時的代碼:

import java.sql.Connection;
import java.util.*;
public class MapDemo {
public static void main(String[] args) {
Map<String ,Integer> maps=new HashMap<>();
Map<String,Integer> maps2=new LinkedHashMap<>();
Map<String,Integer> maps3=new TreeMap<>();
System.out.println(maps2.isEmpty());//判斷是否為空集合,是則返回true,反之
maps.put("food",5);
maps.clear();//清空
maps2.put("long",15);
maps.put("doll",1);
maps.put("Huawei",2);
maps.put("doll",10);//後面的把前面的覆蓋了
maps.put("iphone",2);
maps.put(null,null);
maps.put("people",8);
maps.putAll(maps2);//maps2的所有元素全部仍到maps
maps.remove("people");//刪除特定元素
Integer value1 =maps.get(null);//獲取null的值

System.out.println(maps);
System.out.println(maps.get("iphone")+","+value1);//輸出iphone的值和 null的值

Set<String> keys=maps.keySet();//獲取全部鍵的集合,Set無序不重覆
for (String key: keys){
Integer value=maps.get(key);//獲取對應鍵的值
System.out.println(key+"="+value);
}
Collection<Integer> values=maps.values();//因為值可能有重覆,所以用Collection集合
for (Integer value: values){
for(String key:maps.keySet()){
if(value==maps.get(key)){
System.out.println(value+"值的有"+key);
}
}
}
System.out.println(maps.size());// maps的大小

Set<Map.Entry<String,Integer>> entries=maps.entrySet();//鍵值對方式
System.out.println(entries);
for (Map.Entry<String, Integer> entry : entries) {
String key=entry.getKey();
Integer value=entry.getValue();
System.out.println(key+"-->"+value);
}
//最簡單的遍歷方法
maps.forEach((k,v) ->{
System.out.println(k+"-->"+v);
});
}
}

啤酒問題(遞歸思路)

import java.io.File;
import java.io.IOException;
import java.util.Scanner;
/**
* 啤酒問題:Beer: 2/bottle,4 hats can change a beer,2 empty bottle can change a beer,question:how many bottle can 10 rmb drink?
*/
public class bbb {
public static int totalNumber;
public static int lastBottles;
public static int lastHats;
public static void main(String[] args) {
Scanner sc=new Scanner(System.in);
System.out.println("你帶了多少錢:");
buy(sc.nextInt());
System.out.println("你能喝"+totalNumber+"瓶");
System.out.println("剩餘瓶子數:"+lastBottles);
System.out.println("剩餘蓋子數:"+lastHats);
}
public static void buy(int money){
totalNumber+=money/2;
lastBottles+=money/2;
lastHats+=money/2;
int newNumber=0;
if(lastBottles>=2){
newNumber+=lastBottles/2;
lastBottles=lastBottles%2;
}
if(lastHats>=4){
newNumber+=lastHats/4;
lastHats=lastHats%4;
}
if (newNumber>0){
buy(newNumber*2);
}
}
}

您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • # 本文簡介 帶尬猴! 你是否在使用 `Fabric.js` 時希望能在選中元素後自定義元素樣式或選框(控制角和輔助線)的樣式? ![file](https://img2023.cnblogs.com/other/2700980/202308/2700980-20230823211856528-21 ...
  • > 優雅解決方案在最下麵,小伙伴們兒可以直接前往 😊 > # 背景 在vue3+vite2項目中,我們有時候想要動態綁定資源,比如像下麵的代碼這樣: ```html ``` 實際效果是這樣: ![](https://img2023.cnblogs.com/blog/3153981/202308/3 ...
  • 這裡給大家分享我在網上總結出來的一些知識,希望對大家有所幫助 前言 隨著JavaScript在現代軟體開發中的日益重要地位,Node.js生態系統中的npm成為了不可或缺的工具。在npm管理依賴的過程中,package-lock.json文件的作用日益凸顯。本文將深入探討為什麼要使用package- ...
  • 今天在寫一個選擇器的時候出現一個問題 這個功能需求是:通過選擇器選擇不同的選項,點擊查詢按鈕發送請求,並將響應結果放到一個div中用v-if控制是否顯示。 看似簡單的一個功能,卻出現一個很搞笑的bug。在我選擇一個選項點擊查詢,本應該顯示結果的div沒有顯示出來,而在選擇一個其他選項,不需要點擊查詢 ...
  • ##### 13 CSS 的position屬性 就像photoshop中的圖層功能會把一整張圖片分層一個個圖層一樣,網頁佈局中的每一個元素也可以看成是一個個類似圖層的層模型。層佈局模型就是把網頁中的每一個元素看成是一層一層的,然後通過定位屬性position對元素進行定位擺放,最終實現網頁的佈局。 ...
  • ##### 12 CSS 的float屬性 - 流動佈局 流動模型(Flow),即文檔流,瀏覽器打開HTML網頁時,從上往下,從左往右,逐一載入。 在正常情況下,HTML元素都會根據文檔流來分佈網頁內容的。 文檔流有2大特征: ① 塊狀元素會隨著瀏覽器讀取文檔的順序,自上而下垂直分佈,一行一個的形式 ...
  • 伴隨物流行業的迅猛發展,一體化供應鏈模式的落地,對系統吞吐、系統穩定發出巨大挑戰,庫存作為供應鏈的重中之重表現更為明顯。 ...
  • ### 歡迎訪問我的GitHub > 這裡分類和彙總了欣宸的全部原創(含配套源碼):[https://github.com/zq2599/blog_demos](https://github.com/zq2599/blog_demos) ### 本篇概覽 - 本篇是《java與es8實戰》系列的第二 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...