Java坦克大战

画图基础

先定义画板类, 用于画图

// 定义画板类画板,用于画图
class MyPanel extends JPanel{// Graphics g是一只画笔// Graphics 提供了绘画方法public void paint(Graphics g){super.paint(g);g.drawOval(0,0,100,100);}}

定义窗口类,用于显示画板

// public类继承JFrame,用于定义窗口
public class Painting extends JFrame {public static void main(String[] args) {new Painting();}private MyPanel myPanel = null;public Painting(){myPanel = new MyPanel();// 窗口加入画布this.add(myPanel);this.setSize(500,500);// 设置窗口退出方式this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);// 显示窗口this.setVisible(true);}
}

paint方法被调用情况

  1. 组件第一次在屏幕显示的时候
  2. 窗口大小改变的时候
  3. repaint()方法被调用的时候

Graphics类常用方法

// 画直线
drawLine(int x1, int y1, int x2, int y2)
// 画矩形边框
drawRect(int x, int y, int width, int height)
// 画椭圆边框
drawOval(int x, int y, int width, int height)
// 填充矩形
fillRect(int x, int y, int width, int height)
// 填充椭圆
fillOval(int x, int y, int width, int height)
// 画图片
drawImage(Image img, int x, int y, ImageObserver observer)
g.drawImage(imgae, 0 , 0,889,500,this);
// 获得图片资源
Image image = Toolkit.getDefaultToolkit().getImage(MyPanel.class.getResource("/vertin.png"));
// 画字符串
drawString(String str, int x, int y)
// 设置画笔颜色
setColor(Color c)
// 设置字体
setFont(Font font)
setFont(new Font("宋体",Font.BOLD,20))
// 设置背景色
setBackground(Color c)

Java事件处理

事件源:产生事件的对象,比如按钮,窗口,文本框等
事件监听器:负责监听事件源所发生的事件,当事件发生时,事件监听器会自动调用相应的方法来处理事件
事件:事件源上发生的事情,比如单击,双击,键盘按下,鼠标移动等
事件发生时,事件源创建对象交给事件监听器,事件监听器调用相应的方法处理事件

事件处理流程:

  1. 组件.addXXXListener(监听器对象)
  2. 监听器对象实现接口
  3. 重写接口中的方法

事件监听器接口

  1. 鼠标事件监听器接口:MouseListener
  2. 键盘事件监听器接口:KeyListener
  3. 窗口事件监听器接口:WindowListener

事件监听器适配器

  1. 鼠标事件监听器适配器:MouseAdapter
  2. 键盘事件监听器适配器:KeyAdapter

坦克大战

MyPanel类,用于完成游戏界面绘制

package TankGame;import javax.swing.*;
import java.awt.*;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.Vector;public class MyPanel extends JPanel implements KeyListener {public Player player = null;static Vector<RedEnemy> enemies = new Vector<>();private int enemiesNum = 6;private int points = 0;private int startMode = 0;private String saveAddress  = "d:\\save.dat";public int getPoints() {return points;}public void setPoints(int points) {this.points = points;}public static Vector<RedEnemy> getEnemies() {return enemies;}public static void setEnemies(Vector<RedEnemy> enemies) {MyPanel.enemies = enemies;}public MyPanel(){player = new Player(500, 500);for (int i = 0; i < enemiesNum; ++i) {RedEnemy e = new RedEnemy(10 + 100 * i, 10);enemies.add(e);}}public MyPanel(int startMode){File file = new File(saveAddress);if(startMode == 1 && file.exists()){try {ObjectInputStream oi = new ObjectInputStream(new FileInputStream(saveAddress));this.points = oi.readInt();player = (Player)oi.readObject();int N = oi.readInt();for(int i = 0;i < N;++i){RedEnemy e = (RedEnemy) oi.readObject();enemies.add(e);}} catch (IOException | ClassNotFoundException e) {throw new RuntimeException(e);} finally {}}else if(startMode == 0){player = new Player(500, 500);for (int i = 0; i < enemiesNum; ++i) {RedEnemy e = new RedEnemy(10 + 100 * i, 10);enemies.add(e);}}}@Overridepublic void paint(Graphics g) {super.paint(g);g.fillRect(0,0,1000,750);g.setColor(Color.CYAN);g.setFont(new Font("宋体",Font.BOLD,20));g.drawString("当前得分:" + points,  800, 700);// 绘制坦克if(player.isAlived())drawTank(player.getX(),player.getY(),g,player.getDir(),0);synchronized (player.getBullets()){// 绘制子弹Vector<Bullet> bullets = player.getBullets();for(Bullet b : bullets){switch (b.getType()){case 0:g.setColor(Color.yellow);break;case 1:g.setColor(Color.RED);break;}g.fillOval(b.getX(),b.getY(),10,10);}}synchronized (enemies) {for (Tank e : enemies) {drawTank(e.getX(), e.getY(), g, e.getDir(), 1);}}}public void drawTank(int x,int y,Graphics g,int dir, int type){// type决定颜色switch (type){case 0:// 玩家坦克g.setColor(Color.cyan);break;case 1:// 敌人坦克g.setColor(Color.magenta);break;default:g.setColor(Color.GRAY);}// dir决定方向 0上,1左,2右,3下switch (dir){case 0:g.fill3DRect(x,y,10,60,false);g.fill3DRect(x + 30,y,10,60,false);g.fill3DRect(x + 10,y + 10,20,40,false);g.fillOval(x + 10,y + 20,20,20);g.drawLine(x + 20,y + 30,x + 20,y);break;case 1:g.fill3DRect(x,y,60,10,false);g.fill3DRect(x,y + 30,60,10,false);g.fill3DRect(x + 10,y + 10,40,20,false);g.fillOval(x + 20,y + 10,20,20);g.drawLine(x + 30,y + 20,x ,y + 20);break;case 2:g.fill3DRect(x,y,60,10,false);g.fill3DRect(x,y + 30,60,10,false);g.fill3DRect(x + 10,y + 10,40,20,false);g.fillOval(x + 20,y + 10,20,20);g.drawLine(x + 30,y + 20,x + 60,y + 20);break;case 3:g.fill3DRect(x,y,10,60,false);g.fill3DRect(x + 30,y,10,60,false);g.fill3DRect(x + 10,y + 10,20,40,false);g.fillOval(x + 10,y + 20,20,20);g.drawLine(x + 20,y + 30,x + 20,y + 60);}}@Overridepublic void keyTyped(KeyEvent e) {}@Overridepublic void keyPressed(KeyEvent e) {if(!player.isAlived())return;if(e.getKeyCode() == KeyEvent.VK_J){//System.out.println("射击!");player.shoot();}//dir决定方向 0上,1左,2右,3下if(e.getKeyCode() == KeyEvent.VK_LEFT || e.getKeyCode() == KeyEvent.VK_A){player.setDir(1);player.moveLeft();}if(e.getKeyCode() == KeyEvent.VK_RIGHT || e.getKeyCode() == KeyEvent.VK_D){player.setDir(2);player.moveRight();}if(e.getKeyCode() == KeyEvent.VK_UP || e.getKeyCode() == KeyEvent.VK_W){player.setDir(0);player.moveUp();}if(e.getKeyCode() == KeyEvent.VK_DOWN || e.getKeyCode() == KeyEvent.VK_S){player.setDir(3);player.moveDown();}this.repaint();}@Overridepublic void keyReleased(KeyEvent e) {}
}

TankGame类,用于创建坦克大战游戏的窗口,并让用户在控制台选择是新游戏还是继续上一局游戏

package TankGame;import javax.swing.*;
import java.util.Scanner;public class TankGame extends JFrame {MyPanel myPanel = null;Timer timer = null;Checker checker = null;Saver saver = null;int startMode = 0;public TankGame(int startMode){myPanel = new MyPanel(startMode);timer = new Timer(myPanel.player.getBullets(),myPanel);checker = new Checker(myPanel.player.getBullets(),myPanel);saver = new Saver(myPanel);saver.setDaemon(true);timer.setDaemon(true);checker.setDaemon(true);timer.start();checker.start();saver.start();// 窗口加入画布this.add(myPanel);this.setSize(1000,750);// 设置窗口退出方式this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);this.addKeyListener(myPanel);// 显示窗口this.setVisible(true);}public static void main(String[] args) {Scanner scanner = new Scanner(System.in);//while(true){System.out.println("选择你想要开始的方式:");System.out.println("1. 新游戏");System.out.println("2. 上一次自动存档游戏");int input = scanner.nextInt();switch (input){case 1:new TankGame();break;case 2:new TankGame(1);break;default:new TankGame();break;}//}}public TankGame(){myPanel = new MyPanel();timer = new Timer(myPanel.player.getBullets(),myPanel);checker = new Checker(myPanel.player.getBullets(),myPanel);saver = new Saver(myPanel);saver.setDaemon(true);timer.setDaemon(true);checker.setDaemon(true);timer.start();checker.start();saver.start();// 窗口加入画布this.add(myPanel);this.setSize(1000,750);// 设置窗口退出方式this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);this.addKeyListener(myPanel);// 显示窗口this.setVisible(true);}
}

Tank类,用于实现坦克有关的所有行为,包括坦克的移动、发射子弹、判断是否碰撞等

package TankGame;import java.io.Serializable;
import java.util.Vector;public class Tank implements Collied , Serializable {private int x;private int y;private int dir = 3;     dir决定方向 0上,1左,2右,3下private int speed = 3;private int shootType = 0;private boolean isAlived = true;private boolean restricted = false;public boolean isRestricted() {return restricted;}public void setRestrict(boolean restricted) {this.restricted = restricted;}public boolean isAlived() {return isAlived;}public void setAlived(boolean alived) {isAlived = alived;}public boolean AinB(Tank t1, Tank t2){if(t1.getX() < t2.getX() || t1.getY() < t2.getY()){return false;}int t1x = t1.getX() + (t1.dir == 1 || t1.dir == 2 ? 0 : 20);int t1y = t1.getY() + (t1.dir == 1 || t1.dir == 2 ? 20 : 0);if(t2.dir == 0 || t2.dir == 3){return ((t1x - t2.getX() < 40 && t1y - t2.getY() < 60));}else{return t1x - t2.getX() < 60 &&  t1y - t2.getY() < 40;}}@Overridepublic boolean onCollision(Object o1, Object o2) {if(o1 instanceof Tank && o2 instanceof Tank){Tank t1 = (Tank) o1;Tank t2 = (Tank) o2;return AinB(t1,t2) || AinB(t2,t1);}return false;}public int getShootType() {return shootType;}public void setShootType(int shootType) {this.shootType = shootType;}private static Vector<Bullet> bullets= new Vector<>();public static Vector<Bullet> getBullets() {return bullets;}public void shoot(){//bullets.add(new Bullet(x,y,0,dir,10));switch (dir){case 0:bullets.add(new Bullet(x + 15,y,shootType,dir,10));break;case 1:bullets.add(new Bullet(x ,y + 15,shootType,dir,10));break;case 2:bullets.add(new Bullet(x + 60,y + 15,shootType,dir,10));break;case 3:bullets.add(new Bullet(x + 15,y + 60,shootType,dir,10));break;}} dir决定方向 0上,1左,2右,3下public void moveLeft(){x -= speed;if(x < 0 ){dir = 2;x += speed;}if(restricted){x += (int)(1.5 * speed);}}public void moveRight(){x += speed;if(x >= 930){dir = 1;x -= speed;}if(restricted){x -=  (int)(1.5 * speed);}}public void moveUp(){y -= speed;if(y < 0 ){dir = 3;y += speed;}if(restricted){y += (int)(1.5 * speed);}}public void moveDown(){y += speed;if(y >= 680 ){dir = 0;y -=  speed;}if(restricted){y -= (int)(1.5 * speed);}}public int getDir() {return dir;}public void setDir(int dir) {this.dir = dir;}public int getSpeed() {return speed;}public void setSpeed(int speed) {this.speed = speed;}public Tank(int x, int y) {this.x = x;this.y = y;}public int getX() {return x;}public void setX(int x) {this.x = x;}public int getY() {return y;}public void setY(int y) {this.y = y;}
}

Player类,作为Tank类的子类,用于定义一些玩家坦克特有的属性和方法

package TankGame;public class Player extends Tank{public Player(int x,int y){super(x,y);setSpeed(5);}
}

RedEnemy类,作为Tank类的子类,用于定义一些敌方坦克特有的属性和方法

package TankGame;public class RedEnemy extends Tank{public RedEnemy(int x, int y) {super(x, y);setShootType(1);}public int moveTime = 500;public int shootTime = 1000;public final int MOVETIME = 500;public final int SHOOTTIME = 1000;
}

Bullet类,用于定义坦克发射的子弹的相关属性和方法

package TankGame;public class Bullet implements Collied{private int x;private int y;private int type;private int dir;private int speed;@Overridepublic boolean onCollision(Object o1, Object o2) {if(o2 instanceof Tank){Tank t = (Tank) o2;Bullet b = (Bullet) o1;if(b.getX() < t.getX() || b.getY() < t.getY()) return false;if(t.getDir() == 0 || t.getDir() == 3){return (b.getX() - t.getX() < 40 && b.getY() - t.getY() < 60);}else{return b.getX() - t.getX() < 60 && b.getY() - t.getY() < 40;}}return false;}public int getSpeed() {return speed;}public void setSpeed(int speed) {this.speed = speed;}public Bullet(int x, int y, int type, int dir, int speed) {this.x = x;this.y = y;this.type = type;this.dir = dir; // dir决定方向 0上,1左,2右,3下this.speed = speed;}public Bullet(int x, int y) {this.x = x;this.y = y;}public int getDir() {return dir;}public void setDir(int dir) {this.dir = dir;}public Bullet(int x, int y, int type, int dir) {this.dir = dir;this.type = type;this.y = y;this.x = x;}public int getX() {return x;}public void setX(int x) {this.x = x;}public int getY() {return y;}public void setY(int y) {this.y = y;}public int getType() {return type;}public void setType(int type) {this.type = type;}public void moveLeft(){x -= speed;}public void moveRight(){x += speed;}public void moveUp(){y -= speed;}public void moveDown(){y += speed;}
}

Checker类,用于实现碰撞检测、游戏资源回收等功能

package TankGame;import java.util.Vector;public class Checker extends Thread{private Vector<Bullet> bullets = null;private MyPanel panel = null;private Vector<Bullet> removeBulletArr = new Vector<>();private Vector<RedEnemy> removeEnemiesArr = new Vector<>();private Vector<RedEnemy> enemies;public Checker(Vector<Bullet> bullets) {this.bullets = bullets;}public Checker(Vector<Bullet> bullets,MyPanel panel) {this.bullets = bullets;this.panel = panel;this.enemies = panel.getEnemies();}@Overridepublic void run() {while(true){try {Thread.sleep(10);} catch (InterruptedException e) {throw new RuntimeException(e);}//碰撞判断synchronized (bullets){//System.out.print("A");synchronized (enemies){//System.out.println("B");//检查碰撞for(Bullet b : bullets){if(b.getType() != 0 && b.onCollision(b,panel.player)){panel.player.setAlived(false);//panel.setPoints(panel.getPoints());}if(b.getType() == 1) continue;for(RedEnemy e : enemies) {if (!e.isAlived()) continue;if (b.onCollision(b, e)) {removeBulletArr.add(b);e.setAlived(false);removeEnemiesArr.add(e);panel.setPoints(panel.getPoints() + 10);}}}}}synchronized (enemies){boolean plCanMove = true;for(int i = 0;i < enemies.size();++i){RedEnemy e1 = enemies.get(i);boolean e1CanMove = true;for(int j = 0;j < enemies.size();++j) {if(j == i) continue;RedEnemy e2 = enemies.get(j);if (e1.onCollision(e1, e2)) {e1.setRestrict(true);e2.setRestrict(true);e1CanMove = false;}}Tank t = panel.player;if (e1.onCollision(e1, t)) {e1.setRestrict(true);t.setRestrict(true);e1CanMove = false;plCanMove = false;}if(e1CanMove){e1.setRestrict(false);}}if(plCanMove){panel.player.setRestrict(false);}}synchronized (bullets){//System.out.println(bullets.size());for(Bullet b : removeBulletArr){bullets.remove(b);}removeBulletArr.clear();}synchronized (enemies){//System.out.println(bullets.size());for(RedEnemy e : removeEnemiesArr){enemies.remove(e);}removeEnemiesArr.clear();}//无敌//panel.player.setAlived(true);//检查子弹是否超出边界synchronized (bullets){//System.out.println(bullets.size());for(Bullet b : bullets){if(b.getY() <= 0 || b.getY() >= 750 || b.getX() <= 0 || b.getX() >= 1000){removeBulletArr.add(b);}}for(Bullet b : removeBulletArr){bullets.remove(b);}removeBulletArr.clear();}panel.repaint();}}
}

Collied类,用于定义一个碰撞检测的类,其中包含一个方法,可以检测两个对象是否碰撞

package TankGame;public interface Collied {// 判断是否碰撞的方法boolean onCollision(Object o1,Object o2);
}

Timer类,用于模拟游戏时间流逝,然后根据时间的流逝更新子弹和坦克的位置

package TankGame;import java.awt.*;
import java.util.Vector;public class Timer extends Thread{private Vector<Bullet> bullets= new Vector<>();private MyPanel panel = null;private int deltaTime = 25;Vector<RedEnemy> enemies =  null;public Timer(Vector<Bullet> bullets) {this.bullets = bullets;}public Timer(Vector<Bullet> bullets,MyPanel panel) {this.bullets = bullets;this.panel = panel;enemies =  panel.enemies;}public int getDeltaTime() {return deltaTime;}public void setDeltaTime(int deltaTime) {this.deltaTime = deltaTime;}@Overridepublic void run() {while(true){// 40帧左右try {Thread.sleep(deltaTime);} catch (InterruptedException e) {throw new RuntimeException(e);}// 子弹运动synchronized (bullets){for(Bullet b : bullets){switch (b.getDir()){ dir决定方向 0上,1左,2右,3下case 0:b.moveUp();break;case 1:b.moveLeft();break;case 2:b.moveRight();break;case 3:b.moveDown();break;}}}// 敌人运动int nextDir = 0;synchronized (bullets) {synchronized (enemies) {for (RedEnemy t : enemies) {if (!t.isAlived()) {continue;}t.moveTime -= deltaTime;t.shootTime -= deltaTime;if (t.shootTime < 0) {t.shoot();t.shootTime = t.SHOOTTIME;}if (t.moveTime < 0) {t.moveTime = t.MOVETIME;nextDir = (int) (Math.random() * 4);} else {nextDir = t.getDir();}t.setDir(nextDir);switch (nextDir) {case 0:t.moveUp();break;case 1:t.moveLeft();break;case 2:t.moveRight();break;case 3:t.moveDown();break;}}//System.out.println("release e");}}panel.repaint();}}
}

Saver类,用于保存游戏状态到指定文件中去

package TankGame;import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectOutputStream;
import java.io.PrintStream;
import java.util.Vector;public class Saver extends Thread{private MyPanel panel = null;private int saveInterval = 10000;private String saveAddress  = "d:\\save.dat";private Tank player = null;private Vector<RedEnemy> enemies = null;public Saver(MyPanel panel) {this.panel = panel;this.player = panel.player;this.enemies = panel.getEnemies();}@Overridepublic void run() {while(true){try {Thread.sleep(saveInterval);} catch (InterruptedException e) {throw new RuntimeException(e);}try {ObjectOutputStream op = new ObjectOutputStream(new FileOutputStream(saveAddress));op.writeInt(panel.getPoints());op.writeObject(player);op.writeInt(enemies.size());synchronized (enemies ){for(int i = 0;i < enemies.size();++i){op.writeObject(enemies.get(i));}}op.close();} catch (IOException e) {throw new RuntimeException(e);} finally {}}}
}

项目源于视频:https://www.bilibili.com/video/BV1fh411y7R8?spm_id_from=333.788.videopod.episodes&vd_source=16bf0c507e4a78c3ca31a05dff1bee4e&p=569

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/68535.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Kotlin开发(六):Kotlin 数据类,密封类与枚举类

引言 想象一下&#xff0c;你是个 Kotlin 开发者&#xff0c;敲着代码忽然发现业务代码中需要一堆冗长的 POJO 类来传递数据。烦得很&#xff1f;别急&#xff0c;Kotlin 贴心的 数据类 能帮你自动生成 equals、hashCode&#xff0c;直接省时省力&#xff01;再想想需要多种状…

redis数据安全与性能保障

数据安全与性能保障 1、持久化1.1 快照持久化1.2 AOF持久化1.3 重写/压缩AOF文件 2、复制2.1 Redis复制的启动过程2.2 主从链 3、处理系统故障3.1 验证快照文件和AOF文件 4、事务4.1 java中的redis事务使用 如有侵权&#xff0c;请联系&#xff5e; 如有错误&#xff0c;也欢迎…

数据分析系列--③RapidMiner算子说明及数据预处理

一、算子说明 1.新建过程 2.算子状态灯 状态灯说明: (1)状态指示灯&#xff1a; 红色:指示灯说明有参数未被设置或输入端口未被连接等问题; 黄色:指示灯说明还未执行算子&#xff0c;不管配置是否基本齐全; 绿色:指示灯说明一切正常&#xff0c;已成功执行算子。 (2)三角…

基于Go语言的三甲医院人机与智能体协同环境系统(上.文章部分)

一、引言 1.1 研究背景与意义 1.1.1 三甲医院对高效协同系统的需求 三甲医院作为医疗体系的核心力量,承担着疑难病症诊治、医学科研教学等重要任务,其业务具有高度的复杂性。在日常运营中,三甲医院涉及多个科室,每个科室又包含众多专业领域,各科室之间需要紧密协作,共…

js笔记(黑马程序员)

&#xff08;Web APIs day4&#xff09; 一、日期对象 1.实例化 在代码中发现了 new 关键字时&#xff0c;一般将这个操作称为实例化 创建一个时间对象并获取时间// 1&#xff0e;得到当前时间 2.日期对象方法 因为日期对象返回的数据我们不能直接使用&#xff0c;所以需…

Java基础知识总结(三十)--泛型

jdk1.5版本以后出现的一个安全机制。表现格式&#xff1a;< > 好处&#xff1a; 1&#xff1a;将运行时期的问题ClassCastException问题转换成了编译失败&#xff0c;体现在编译时期&#xff0c;程序员就可以解决问题。 2&#xff1a;避免了强制转换的麻烦。 只要带有…

SOME/IP--协议英文原文讲解2

前言 SOME/IP协议越来越多的用于汽车电子行业中&#xff0c;关于协议详细完全的中文资料却没有&#xff0c;所以我将结合工作经验并对照英文原版协议做一系列的文章。基本分三大块&#xff1a; 1. SOME/IP协议讲解 2. SOME/IP-SD协议讲解 3. python/C举例调试讲解 4.1 Speci…

python-leetcode-反转链表 II

92. 反转链表 II - 力扣&#xff08;LeetCode&#xff09; # Definition for singly-linked list. # class ListNode: # def __init__(self, val0, nextNone): # self.val val # self.next next class Solution:def reverseBetween(self, head: Optional…

LM Studio 本地部署DeepSeek及其他AI模型的详细操作教程及硬件要求

本篇文章主要讲解&#xff0c;通过LM Studio工具实现各类型AI模型本地部署的操作方法方式。 作者&#xff1a;任聪聪 日期&#xff1a;2025年1月29日 LM Studio 介绍&#xff1a; LM Studio是一款能够本地离线运行各类型大语言模型的客户端应用&#xff0c;通过LM Studio 可以…

SOME/IP--协议英文原文讲解3

前言 SOME/IP协议越来越多的用于汽车电子行业中&#xff0c;关于协议详细完全的中文资料却没有&#xff0c;所以我将结合工作经验并对照英文原版协议做一系列的文章。基本分三大块&#xff1a; 1. SOME/IP协议讲解 2. SOME/IP-SD协议讲解 3. python/C举例调试讲解 Note: Thi…

doris:HLL

HLL是用作模糊去重&#xff0c;在数据量大的情况性能优于 Count Distinct。HLL的导入需要结合hll_hash等函数来使用。更多文档参考HLL。 使用示例​ 第 1 步&#xff1a;准备数据​ 创建如下的 csv 文件&#xff1a;test_hll.csv 1001|koga 1002|nijg 1003|lojn 1004|lofn …

在Rust应用中访问.ini格式的配置文件

在Rust应用中访问.ini格式的配置文件&#xff0c;你可以使用第三方库&#xff0c;比如 ini 或 config. 下面是一个使用 ini 库的示例&#xff0c;该库允许你读取和解析.ini文件。 使用 ini 库 添加依赖 首先&#xff0c;你需要在你的 Cargo.toml 文件中添加 ini 库的依赖&am…

Janus Pro:DeepSeek 开源革新,多模态 AI 的未来

Janus Pro 是 DeepSeek 开发的一个开源多模态人工智能框架&#xff0c;它通过集成视觉和语言处理能力&#xff0c;提供了高性能的多模态任务处理能力。 在线体验&#xff1a; https://deepseek-januspro.com/ 背景 Janus Pro 于2025年1月发布&#xff0c;是一个开源的多模态…

Jenkins上生成的allure report打不开怎么处理

目录 问题背景&#xff1a; 原因&#xff1a; 解决方案&#xff1a; Jenkins上修改配置 通过Groovy脚本在Script Console中设置和修改系统属性 步骤 验证是否清空成功 进一步的定制 也可以使用Nginx去解决 使用逆向代理服务器Nginx&#xff1a; 通过合理调整CSP配置&a…

指针的介绍3前

1.字符指针变量 1.1介绍 char arr[] "abcdef";char* p arr; 上面的代码中&#xff0c;我创建了 字符数组 arr 来存储一个字符串 此时&#xff0c;我可以创建一个指针变量对这个字符串进行相应的修改&#xff1a; 我也可以创建一个指针变量指向一个字符串&#xff…

Scrapy如何设置iP,并实现IP重用, IP代理池重用

前置知识 1/3乐观锁 2/3 Scrapy流程(非全部) 3/3 关于付费代理 我用的"快代理", 1000个ip, 每个ip1min的有效期, 你用的时候, 把你的链接, 用户名填上去就行 设置代理IP &#x1f512; & 帮助文档: ①meta ②meta#proxy$ 语法: ①proxy的设置: Request对象中…

gesp(C++六级)(7)洛谷:P10376:[GESP202403 六级] 游戏

gesp(C六级)&#xff08;7&#xff09;洛谷&#xff1a;P10376&#xff1a;[GESP202403 六级] 游戏 题目描述 你有四个正整数 n , a , b , c n,a,b,c n,a,b,c&#xff0c;并准备用它们玩一个简单的小游戏。 在一轮游戏操作中&#xff0c;你可以选择将 n n n 减去 a a a&am…

es数据同步

Logstash 是 Elastic 技术栈中的一个技术&#xff0c;它是一个数据采集引擎&#xff0c;可以从数据库采集数据到 ES 中。可以通过设置 自增 ID 主键 或 更新时间 来控制数据的自动同步&#xff1a; 自增 ID 主键&#xff1a;Logstatsh 会有定时任务&#xff0c;如果发现有主键…

【16届蓝桥杯寒假刷题营】第2期DAY5

5.变变数组 - 蓝桥云课 给定一个长度为 n 的整数数组 A&#xff0c;A 中第 i 个元素为 Ai​&#xff08;1≤i≤n&#xff09;&#xff0c;你只能在 A 中选择一个元素 a&#xff0c;将 A 中所有数值等于 a 的元素变为 a2&#xff0c;请问变化后 A 中所有元素和的最大为多少。 …

【flutter版本升级】【Nativeshell适配】nativeshell需要做哪些更改

flutter 从3.13.9 升级&#xff1a;3.27.2 nativeshell组合库中的 1、nativeshell_build库替换为github上的最新代码 可以解决两个问题&#xff1a; 一个是arg("--ExtraFrontEndOptions--no-sound-null-safety") 在新版flutter中这个构建参数不支持了导致的build错误…