@[toc]
一,前言
今天写多线程学习心得,为了深入了解多线程的操作。
之前学习过Go的多线程,有着,异曲同工之妙。
二,多任务
比如:边吃饭边看手机。同时做好几个任务。
三,多线程
原来是一条任务通道,因为任务太多,会发生通道堵塞,大大降低了效率。
为了解决这个问题。充分的利用道路,变成了多个通道。
目的:俩个任务同时执行。
四,程序,进程,线程
操作系统运行的程序就是进程。一个进程里可以有多个线程。
例子:视频:声音,图像,字幕。
Process,Thread。
程序:静态。
进程:动态。
线程是cpu调度和执行的单位。
注意:
现在我们写的很多多线程都是模拟出来的,正在的线程指的是多个CPU,模拟出来的线程的话,在一个cpu里,切换的很快,有一种多线程的错觉。
五,线程创建。
1,继承Thread类创建线程类
2,通过Runnable接口创建线程类
3,通过Callable和Future创建线程
5.1,Thread类
1,自定义线程类继承Thread类
2,重写run()方法,写编程执行体
3,创建线程对象,调用start()方法,启动线程。
1,先继承extends Thread
public class testthread extends Thread
2,然后重写run方法,run方法线程体
@Override
public void run() {
for (int i=0;i<20;i++) {
System.out.println("你好上进小菜猪" + i);
}
}
3,创建主线程,main,主线程,创建一个线程对象
testthread testthread1 =new testthread();
4,调用start()方法开启线程
testthread1.start();
5,下面写一下主线程输出内容。
for (int i=0;i<20;i++)
{
System.out.println("这是多线程"+i);
}
6,跑一下看看结果。
观察发现,交替执行。
因为start()方法在主线程上面,所以,先执行子线程,然后交替执行主线程与子线程。
注意:线程不一定执行,cpu调度安排。
总结:
1,继承Thread类。
线程不一定立即执行,由cpu调度安排。
六,附源码
testthread类详情如下
package Multithreading;
import xsthr4.TestThread;
//创建线程方式一,重写run方法,调用start开启线程
public class testthread extends Thread{
@Override
public void run() {
//run方法线程体
for (int i=0;i<20;i++) {
System.out.println("你好上进小菜猪" + i);
}
}
public static void main(String[] args) {
//main,主线程
//创建一个线程对象
testthread testthread1 =new testthread();
//调用start()方法开启线程
testthread1.start();
for (int i=0;i<20;i++)
{
System.out.println("这是多线程"+i);
}
}
}
CopyOfTCPGSONServer类详情如下
package work2067111119;
import java.io.IOException;
import java.io.InputStream;
import java.io.ObjectInputStream;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import com.google.gson.Gson;
/*
* 服务器端
*
* 绑定端口10010
*
* 接收客户端的数据(字符串)
*/
class MyRunable implements Runnable {
Socket client;// 定义变量,保存接收的数据
// 构造方法的参数来接收数据
public MyRunable(Socket s) {
// TODO Auto-generated constructor stub
client = s;
}
static UserDAO service = new UserDAO();
@Override
public void run() {
// 线程需要从客户端获取数据,验证,将验证结果发送给客户端
// Socket对象,封装io流
// TODO Auto-generated method stub
// [3]获取客户端的数据
// io流,和客户端和服务器的连接服务中封装
InputStream is;
try {
is = client.getInputStream();
byte[] buf = new byte[1024];
int len = is.read(buf);
String data = new String(buf, 0, len);// 客户端发过来的json字符串
// 将json字符串转换成UserBean对象
Gson gson = new Gson();
UserBean user = gson.fromJson(data, UserBean.class);// 第一个参数要转换的字符串,第二个参数是转换的类型
String ip = client.getInetAddress().getHostAddress();
String xp = user.toString();
String[] tokens=xp.split(",");
System.out.println(tokens[0]);
System.out.println("接收到 " + ip + " 数据:" + user);
if(tokens[0].equals(String.valueOf('0'))){
System.out.println("执行注册操作");
String result;
result= service.addUser(tokens[1],tokens[2]);
System.out.println("验证结果:"+result);
OutputStream out=client.getOutputStream();
out.write(result.getBytes());
out.flush();
System.out.println("将验证结果发送给客户端");
client.close();
}
if(tokens[0].equals(String.valueOf('1'))){
System.out.println("执行登录操作");
String result;
result=service.sign(tokens[1],tokens[2]);
System.out.println("验证结果:"+result);
OutputStream out=client.getOutputStream();
out.write(result.getBytes());
out.flush();
System.out.println("将验证结果发送给客户端");
client.close();
}
} catch (IOException | SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
public class CopyOfTCPGSONServer {
public static void main(String[] args) throws IOException,
ClassNotFoundException, SQLException {
// TODO Auto-generated method stub
System.out.println("服务器启动");
// [1]创建服务,服务器端Serversocket
int port = 9898;
ServerSocket server = new ServerSocket(port);
while (true) {
// [2]接入客户端
Socket client = server.accept();// 阻塞式的方法,没有客户端接入,就会一直等待
System.out.println("接入一个客户端");
// in.next();//阻塞式的方法,没有输入的话,就会一直停留在这个位置
// 为这个客户端启动一个线程,用线程给客户端提供服务(接收,验证,发送)
// 方案2创建线程
MyRunable r = new MyRunable(client);
Thread serverThread = new Thread(r);
serverThread.start();
}
}
}
UserDao类代码详解如下:
package work2067111119;//import com.mysql.jdbc.Connection;
import java.sql.*;
public class UserDAO {
//Connection conn=(Connection) JDBCUtlis.getConnection();
Connection conn = (Connection) JDBCUtils.getConnection();
//查找user_info所有记录
public ResultSet searchAll() throws SQLException {
Statement stmt = conn.createStatement();
String sql = "select * from tcpcheck";//表名
//String sql ="select * from eat order by time desc";
ResultSet rs = stmt.executeQuery(sql);
return rs;
}
public String addUser(String username, String password) throws SQLException {
String sql1="SELECT * FROM tcpcheck WHERE username=?";
PreparedStatement pStatement=conn.prepareStatement(sql1);
pStatement.setString(1,username );
ResultSet rs=pStatement.executeQuery();
String result="";//验证结果
if(rs.next()){
result="注册失败,用户名已经被占用!";
}else{
String sql = "INSERT INTO tcpcheck(username,password) VALUES(?,?)";
PreparedStatement pstmt = (PreparedStatement) conn.prepareStatement(sql);
//pstmt.setString(1, uid);
pstmt.setString(1, username);
pstmt.setString(2, password);
pstmt.executeUpdate();
result="注册成功";
}
return result;
}
public String sign(String token, String token1) throws SQLException {
String sql="SELECT * FROM tcpcheck WHERE username=? AND password=?";
PreparedStatement pStatement=conn.prepareStatement(sql);
pStatement.setString(1,token );
pStatement.setString(2,token1 );
ResultSet rs=pStatement.executeQuery();
String result="";//验证结果
if(rs.next()){
result="登录成功";
}else{
result="登录失败";
}
return result;
}
}
UserBand详情如下
```package work2067111119;
import java.io.Serializable;
public class UserBean implements Serializable {
private String username;//用户名
private String password;//密码
private String type;//密码
//构造方法,带参数
public UserBean(String type, String username, String password) {
this.username = username;
this.password = password;
this.type = type;}
@Override
br/>}
@Override
// TODO Auto-generated method stub
return type+","+username+","+password;
}
}
# 七,下篇预告
下篇写,继承Runnable类详解。
