Python实现2048小游戏

2048是一个单人益智游戏,目标是移动和合并数字,以达到2048。

1. 实现效果

Python实现2048小游戏

2. 游戏规则

简单地理解一下规则

基本规则:

  • 4x4棋盘,每个格可包含一个2的倍数的数字,初始时为空,表示0。
  • 游戏开始时,格中会随机生成两个数,数字通常为2或4。
  • 可通过键盘的上下左右方向来驱使所有的块向同一方向移,直至无法移动。
  • 移动过程,途遇相同数字,二者合并后的数字为原来的两倍,且仅合并一对为1个数字。
  • 移动后,随机生成一个新的2或4方块。
  • 每次合并方块时,得分会增加,得分等于合并后新方块的数字。
  • 游戏结束:网格中没有空位置且没有可以合并的方块时game over
  • 重启游戏:点击“Restart”按钮可以重启游戏。
  • 高分记录:可以查看之前的高分,并可以输入姓名记录自己的得分。

其他规则:

  1. 实现游戏规则。
  2. 使用图形函数生成界面等。 【分数+游戏局+重玩+分数排行】
  3. 用文件存储用户的进度。【游戏进度实时记录于save_game.txt便于继续残局】
  4. 用户开始新游戏时,先检测是否有历史记录,有的话可以继续未完成的游戏,也可以重新开始。
  5. 实现用户排名功能,要求能够将排名信息进行保存,存至文件永久保存。【存至high_scores.json文件】
  6. 当新用户的成绩需要插入排名列表时,要能够修改原列表信息:如果是同一用户需要更新成绩,则覆盖原成绩。【Score按钮】
  7. 可以插入、修改、删除排名信息。【Score按钮,点击显示弹窗,当中的排名信息可以增删改】

3. 环境配置

程序中会用到的库:

import tkinter as tk
import random
import json
import os

其中os、json和random是python的内置库,不需要安装,tkinter是标准库之一,通常也不需要单独安装。

4. 代码实现

变量说明

# 设置游戏参数
self.grid_size = 4 # 4×4格
self.score = 0     # 当前局的分数
self.high_score = self.load_highest_score() # 最高分记录
self.tile_values = [[0] * self.grid_size for _ in range(self.grid_size)] # 数字块初始值为 0
self.game_over = False # 判断游戏是否结束的标志

游戏界面

"""创建游戏界面"""
# 组件部分
# 上层:构建框架frame 包含2个文本标签:当前分数score和最高分数Highest Score
self.frame = tk.Frame(self.root, bg="#faf8ef", padx=10, pady=10)
self.frame.pack(pady=20)
# 分数标签 在frame中加score标签 显示当前游戏分数
self.score_label = tk.Label(self.frame, text=f"Score: {self.score}", font=("Arial", 18), bg="#faf8ef")
self.score_label.grid(row=0, column=0,padx=10,)
# 最高分标签 在frame中加high_score标签 显示最高游戏分数
self.high_score_label = tk.Label(self.frame, text=f"Highest Score: {self.high_score}", font=("Arial", 18),
                                 bg="#faf8ef")
self.high_score_label.grid(row=0, column=1,padx=10,)
# 中层:创建画布 画布用于绘制游戏块
self.canvas = tk.Canvas(self.root, width=400, height=400, highlightthickness=0)
self.canvas.pack()
# 下层:构建框架frame1 包含2个按钮, 1个标签:重来按钮restart+信息按钮Scores+游戏结束标签
self.frame1 = tk.Frame(self.root, bg="#faf8ef")
self.frame1.pack(pady=20)
self.restart_button = tk.Button(self.frame1, text="Restart", command=self.restart_game, font=("Arial", 16),
                                bg="#8f7a66", fg="white", relief=tk.FLAT)
self.high_scores_button = tk.Button(self.frame1, text="Scores", command=self.show_high_scores,
                                    font=("Arial", 16), bg="#8f7a66", fg="white", relief=tk.FLAT)
# 布局按钮
self.restart_button.grid(row=0, column=0, padx=20)
self.high_scores_button.grid(row=0, column=1, padx=20)

棋盘绘制

tile_colors = {0: "#D9D5D1", 2: "#eee4da", 4: "#ede0c8", 8: "#f2b179",
            16: "#f59563", 32: "#f67c5f", 64: "#f67c5f", 128: "#f9f6f2",
        256: "#f9f6f2", 512: "#f9f6f2", 1024: "#f9f6f2", 2048: "#f9f6f2",} # 数字砖块颜色渐变

数字块背景色渐变
不同的数字格子背景颜色不同

假设值,看一下配色

{"tiles": [[2, 4, 6, 16], [32, 64, 128, 256], [512, 1024, 2048, 4096], [8192, 16384, 32768, 65536]], "score": 11223243436}

2 ~ 2048有设置配色,后面更大的数就默认了,不过为了颜色不太杂乱,设置的颜色也少。

在这里插入图片描述

块的数字值设置

# 绘制每个方块
for y in range(self.grid_size):
    for x in range(self.grid_size):
        value = self.tile_values[y][x] # 块的数字值
        color = tile_colors.get(value, "#cdc1b4")  # 默认颜色
        self.canvas.create_rectangle(x * 100 + 5, y * 100 + 5, (x + 1) * 100 - 5, (y + 1) * 100 - 5, fill=color, outline="#bfb3a0", width=8, tags='tile') # 画布绘制正方形块 初始块 就是0的状态, 此时砖块无数值
        if value != 0: # 当 value ≥ 0 给砖块加入数值文字
            self.canvas.create_text(x * 100 + 50, y * 100 + 50,text=str(value), font=("Arial", 24), fill="#776e65")

分数显示部分

self.high_score = self.load_highest_score()
self.high_score_label.config(text=f"Highest Score: {self.high_score}")

存在一个问题, 就是第一次运行时, 文件不存在, 然后获取最高分数是从文档获取的,所以这个时候会是0。

def load_highest_score(self):
    """加载最高分"""
    if os.path.exists("high_scores.json"):
        with open("high_scores.json", "r") as f:
            high_scores = json.load(f)
            if high_scores:
                return high_scores[0][1]  # 返回最高分
    return 0

因此,预防第一局时, 还没有历史记录, 最高分数睡懒觉 设置为当没有最高分数时让最高分数跟随当前分数score。

几个特殊情况的最高分数值显示:一个是初始时没有文档最高值记录,此时应跟随score。然后我存入一最高分,① 游戏未结束,并不restart继续玩,此时应仍旧跟随;② 此时若restart 应从文档中取;③ 若此时我继续玩一会又restart 此时应从文档中取。

self.high_score = self.load_highest_score()
if self.high_score==0 or self.score > self.high_score:
        self.high_score_label.config(text=f"Highest Score: {self.score}")
else:
    self.high_score_label.config(text=f"Highest Score: {self.high_score}")

动作部分

随机新数
在空白方块上生成一个新的数字方块(2或4)

def spawn_tile(self):
    empty_tiles = [(x, y) for x in range(self.grid_size) for y in range(self.grid_size) if
                   self.tile_values[y][x] == 0]
    if empty_tiles:
        x, y = random.choice(empty_tiles)
        self.tile_values[y][x] = random.choice([2, 4]) # 一般是2或者4这种比较小的数值

上下左右

def move(self, direction):
    """根据方向移动方块并合并"""
    original_tiles = [row[:] for row in self.tile_values]  # 记录原始状态
    merged = [[False] * self.grid_size for _ in range(self.grid_size)]
    if direction == "Left":
        for x in range(self.grid_size):
            self.tile_values[x] = self.merge_row_left(self.tile_values[x])
    elif direction == "Right":
        for i in range(self.grid_size):
            self.tile_values[i] = self.merge_row_left(self.tile_values[i][::-1])[::-1]
    elif direction == "Up":
        for j in range(self.grid_size):
            col = [self.tile_values[i][j] for i in range(self.grid_size)]
            merged_col = self.merge_row_left(col)
            for i in range(self.grid_size):
                self.tile_values[i][j] = merged_col[i]
    elif direction == "Down":
        for j in range(self.grid_size):
            col = [self.tile_values[i][j] for i in range(self.grid_size)]
            merged_col = self.merge_row_left(col[::-1])[::-1]
            for i in range(self.grid_size):
                self.tile_values[i][j] = merged_col[i]
    # 如果发生了移动或合并,则生成新的方块
    if original_tiles != self.tile_values:
        self.spawn_tile()

合并&积分

def merge_row_left(self, row):
    """将给定行向左合并"""
    new_row = [num for num in row if num != 0]  # 去除零
    merged_row = []
    index = 0
    while index < len(new_row):
        # 如果相邻两个相同,则合并
        if index + 1 < len(new_row) and new_row[index] == new_row[index + 1]:
            merged_value = new_row[index] * 2
            merged_row.append(merged_value)  # 添加合并后的值
            self.score += merged_value  # 更新分数
            index += 2  # 跳过下一个值
        else:
            merged_row.append(new_row[index])
            index += 1
    # 填充剩余的零
    while len(merged_row) < self.grid_size:
        merged_row.append(0)
    return merged_row

数据存储

游戏进度保存

在这里插入图片描述

def save_game(self):
    """保存当前游戏状态 游戏实时存档"""
    data = {'tiles': self.tile_values, 'score': self.score}
    with open("save_game.txt", "w") as f:
        json.dump(data, f)

每移动一步都会被记录下来,所以中断游戏的时候,用户下次再玩,开始新游戏时,加载游戏时,会先检测是否有历史记录,有的话可以继续未完成的游戏,也可以重新开始。
在这里插入图片描述

游戏加载

def load_game(self):
    """加载游戏状态 先查看是否存在残局, 有则恢复, 无则重开一局"""
    if os.path.exists("save_game.txt"):
        with open("save_game.txt", "r") as f:
            data = json.load(f)
            self.tile_values = data['tiles']
            self.score = data['score']
    else:
        self.restart_game()

高分保存

将用户排名信息进行保存,存至文件永久保存。

def save_high_scores(self, scores):
    """保存高分记录"""
    with open("high_scores.json", "w") as f:
        json.dump(scores, f)

重来一局

game over判断

def check_game_over(self):
    """检查游戏是否结束"""
    if any(0 in row for row in self.tile_values):
        return False  # 如果还有空方块,游戏未结束
    for i in range(self.grid_size):
        for j in range(self.grid_size):
            # 检查相邻方块是否可以合并
            if (i < self.grid_size - 1 and self.tile_values[i][j] == self.tile_values[i + 1][j]) or \
                    (j < self.grid_size - 1 and self.tile_values[i][j] == self.tile_values[i][j + 1]):
                return False  # 还有可以合并的方块
    return True  # 无法再移动或合并,游戏结束

显示game over

def show_game_over(self):
    """显示游戏结束的信息"""
    if not hasattr(self, 'game_over_label'):
        self.game_over_label = tk.Label(self.frame1, text="Game Over!", font=('Arial', 24), fg="red", bg="#faf8ef")
        self.game_over_label.grid(row=0, column=2, padx=20)

restart的话,这个game over的label就要清掉,但又不能影响下一局的判断,所以加了判断:

if not hasattr(self, 'game_over_label'):

游戏重来

def restart_game(self):
    """重启游戏"""
    self.tile_values = [[0] * self.grid_size for _ in range(self.grid_size)]
    self.score = 0
    self.game_over = False
    # 清除游戏结束的标签(如果有的话)
    if hasattr(self, 'game_over_label'):
        self.game_over_label.destroy()  # 移除游戏结束的文本
        del self.game_over_label  # 删除引用
    self.spawn_tile()
    self.spawn_tile()  # 在两个随机位置生成方块
    self.draw_board()
    self.save_game()

分数排行

在这里插入图片描述

排行榜的分数增删( 包含改,同一个用户可以多次等级分数,会自动择高分)

def add_high_score(self, score_window):
    """添加新的高分记录"""
    def submit_score():
        name = entry.get()
        if name:
            score_list = self.load_high_scores()
            exists = False
            for i, (n, sc) in enumerate(score_list):
                if n == name:  # 如果名称已存在则更新分数
                    score_list[i][1] = max(sc, self.score)
                    exists = True
                    break
            if not exists:
                score_list.append([name, self.score])  # 新增高分
            score_list.sort(key=lambda x: x[1], reverse=True)  # 根据分数排序
            score_list = score_list[:10]  # 只保留前10名
            self.save_high_scores(score_list)
            score_window.destroy()  # 关闭添加窗口
            self.show_high_scores()  # 更新高分显示
def delete_high_score(self, name):
    """删除某个玩家的高分记录"""
    score_list = self.load_high_scores()
    score_list = [item for item in score_list if item[0] != name]
    self.save_high_scores(score_list)
    self.show_high_scores()

完整代码

import tkinter as tk
import random
import json
import os
class Game2048:
    def __init__(self, root):
        self.root = root  # 主窗口
        root.title("2048 Game") # 窗口标题
        # 设置游戏参数
        self.grid_size = 4 # 4×4格
        self.score = 0     # 当前局的分数
        self.high_score = self.load_highest_score() # 最高分记录
        self.tile_values = [[0] * self.grid_size for _ in range(self.grid_size)] # 数字块初始值为 0
        self.game_over = False # 判断游戏是否结束的标志
        self.create_ui()  # 创建ui
        self.load_game()  # 加载游戏
        self.spawn_tile() # 随机新增数字块
        self.draw_board() # 绘制游戏局
        root.bind("<Key>", self.key_pressed) # 绑定键盘事件到root窗口

    def create_ui(self):
        """创建游戏界面"""
        # 组件部分
        # 上层:构建框架frame 包含2个文本标签:当前分数score和最高分数Highest Score
        self.frame = tk.Frame(self.root, bg="#faf8ef", padx=10, pady=10)
        self.frame.pack(pady=20)
        # 分数标签 在frame中加score标签 显示当前游戏分数
        self.score_label = tk.Label(self.frame, text=f"Score: {self.score}", font=("Arial", 18), bg="#faf8ef")
        self.score_label.grid(row=0, column=0,padx=10,)
        # 最高分标签 在frame中加high_score标签 显示最高游戏分数
        self.high_score_label = tk.Label(self.frame, text=f"Highest Score: {self.high_score}", font=("Arial", 18),
                                         bg="#faf8ef")
        self.high_score_label.grid(row=0, column=1,padx=10,)
        # 中层:创建画布 画布用于绘制游戏块
        self.canvas = tk.Canvas(self.root, width=400, height=400, highlightthickness=0)
        self.canvas.pack()
        # 下层:构建框架frame1 包含2个按钮, 1个标签:重来按钮restart+信息按钮Scores+游戏结束标签
        self.frame1 = tk.Frame(self.root, bg="#faf8ef")
        self.frame1.pack(pady=20)
        self.restart_button = tk.Button(self.frame1, text="Restart", command=self.restart_game, font=("Arial", 16),
                                        bg="#8f7a66", fg="white", relief=tk.FLAT)
        self.high_scores_button = tk.Button(self.frame1, text="Scores", command=self.show_high_scores,
                                            font=("Arial", 16), bg="#8f7a66", fg="white", relief=tk.FLAT)
        # 布局按钮
        self.restart_button.grid(row=0, column=0, padx=20)
        self.high_scores_button.grid(row=0, column=1, padx=20)

    def draw_board(self):
        """绘制棋盘"""
        self.canvas.delete("all")  # 清空画布
        tile_colors = {0: "#D9D5D1", 2: "#eee4da", 4: "#ede0c8", 8: "#f2b179",
                    16: "#f59563", 32: "#f67c5f", 64: "#f67c5f", 128: "#f9f6f2",
                256: "#f9f6f2", 512: "#f9f6f2", 1024: "#f9f6f2", 2048: "#f9f6f2",} # 数字砖块颜色渐变
        # 绘制每个方块
        for y in range(self.grid_size):
            for x in range(self.grid_size):
                value = self.tile_values[y][x] # 块的数字值
                color = tile_colors.get(value, "#cdc1b4")  # 默认颜色
                self.canvas.create_rectangle(x * 100 + 5, y * 100 + 5, (x + 1) * 100 - 5, (y + 1) * 100 - 5, fill=color, outline="#bfb3a0", width=8, tags='tile') # 画布绘制正方形块 初始块 就是0的状态, 此时砖块无数值
                if value != 0: # 当 value ≥ 0 给砖块加入数值文字
                    self.canvas.create_text(x * 100 + 50, y * 100 + 50,text=str(value), font=("Arial", 24), fill="#776e65")
        self.score_label.config(text=f"Score: {self.score}")
        self.high_score = self.load_highest_score()
        if self.high_score==0 or self.score > self.high_score:
                self.high_score_label.config(text=f"Highest Score: {self.score}")
        else:
            self.high_score_label.config(text=f"Highest Score: {self.high_score}")
            
    def load_game(self):
        """加载游戏状态 先查看是否存在残局, 有则恢复, 无则重开一局"""
        if os.path.exists("save_game.txt"):
            with open("save_game.txt", "r") as f:
                data = json.load(f)
                self.tile_values = data['tiles']
                self.score = data['score']
        else:
            self.restart_game()

    def load_highest_score(self):
        """加载最高分"""
        if os.path.exists("high_scores.json"):
            with open("high_scores.json", "r") as f:
                high_scores = json.load(f)
                if high_scores:
                    return high_scores[0][1]  # 返回最高分
        return 0

    def save_game(self):
        """保存当前游戏状态 游戏实时存档"""
        data = {'tiles': self.tile_values, 'score': self.score}
        with open("save_game.txt", "w") as f:
            json.dump(data, f)

    def spawn_tile(self):
        """在空白方块上生成一个新的数字方块(2或4) 新增数字砖块 add new_tile"""
        empty_tiles = [(x, y) for x in range(self.grid_size) for y in range(self.grid_size) if
                       self.tile_values[y][x] == 0]
        if empty_tiles:
            x, y = random.choice(empty_tiles)
            self.tile_values[y][x] = random.choice([2, 4]) # 一般是2或者4这种比较小的数值

    def key_pressed(self, event):
        """处理键盘按键事件"""
        if self.game_over:
            return
        if event.keysym in ['Up', 'Down', 'Left', 'Right']:
            self.move(event.keysym)
            self.save_game()
            self.draw_board()
            if self.check_game_over():
                self.game_over = True
                self.show_game_over()

    def check_game_over(self):
        """检查游戏是否结束"""
        if any(0 in row for row in self.tile_values):
            return False  # 如果还有空方块,游戏未结束
        for i in range(self.grid_size):
            for j in range(self.grid_size):
                # 检查相邻方块是否可以合并
                if (i < self.grid_size - 1 and self.tile_values[i][j] == self.tile_values[i + 1][j]) or \
                        (j < self.grid_size - 1 and self.tile_values[i][j] == self.tile_values[i][j + 1]):
                    return False  # 还有可以合并的方块
        return True  # 无法再移动或合并,游戏结束

    def show_game_over(self):
        """显示游戏结束的信息"""
        if not hasattr(self, 'game_over_label'):
            self.game_over_label = tk.Label(self.frame1, text="Game Over!", font=('Arial', 24), fg="red", bg="#faf8ef")
            self.game_over_label.grid(row=0, column=2, padx=20)

    def move(self, direction):
        """根据方向移动方块并合并"""
        original_tiles = [row[:] for row in self.tile_values]  # 记录原始状态
        merged = [[False] * self.grid_size for _ in range(self.grid_size)]
        if direction == "Left":
            for x in range(self.grid_size):
                self.tile_values[x] = self.merge_row_left(self.tile_values[x])
        elif direction == "Right":
            for i in range(self.grid_size):
                self.tile_values[i] = self.merge_row_left(self.tile_values[i][::-1])[::-1]
        elif direction == "Up":
            for j in range(self.grid_size):
                col = [self.tile_values[i][j] for i in range(self.grid_size)]
                merged_col = self.merge_row_left(col)
                for i in range(self.grid_size):
                    self.tile_values[i][j] = merged_col[i]
        elif direction == "Down":
            for j in range(self.grid_size):
                col = [self.tile_values[i][j] for i in range(self.grid_size)]
                merged_col = self.merge_row_left(col[::-1])[::-1]
                for i in range(self.grid_size):
                    self.tile_values[i][j] = merged_col[i]
        # 如果发生了移动或合并,则生成新的方块
        if original_tiles != self.tile_values:
            self.spawn_tile()

    def merge_row_left(self, row):
        """将给定行向左合并"""
        new_row = [num for num in row if num != 0]  # 去除零
        merged_row = []
        index = 0
        while index < len(new_row):
            # 如果相邻两个相同,则合并
            if index + 1 < len(new_row) and new_row[index] == new_row[index + 1]:
                merged_value = new_row[index] * 2
                merged_row.append(merged_value)  # 添加合并后的值
                self.score += merged_value  # 更新分数
                index += 2  # 跳过下一个值
            else:
                merged_row.append(new_row[index])
                index += 1
        # 填充剩余的零
        while len(merged_row) < self.grid_size:
            merged_row.append(0)
        return merged_row

    def restart_game(self):
        """重启游戏"""
        self.tile_values = [[0] * self.grid_size for _ in range(self.grid_size)]
        self.score = 0
        self.game_over = False
        # 清除游戏结束的标签(如果有的话)
        if hasattr(self, 'game_over_label'):
            self.game_over_label.destroy()  # 移除游戏结束的文本
            del self.game_over_label  # 删除引用
        self.spawn_tile()
        self.spawn_tile()  # 在两个随机位置生成方块
        self.draw_board()
        self.save_game()

    def show_high_scores(self):
        """显示高分记录"""
        score_window = tk.Toplevel(self.root)
        score_window.title("Rank")
        score_window.configure(bg="#faf8ef")
        score_list = self.load_high_scores()
        for index, (name, score) in enumerate(score_list):
            frame = tk.Frame(score_window, bg="#faf8ef")
            frame.pack(pady=5)
            tk.Label(frame, text=f"{index + 1}. {name}: {score}", font=("Arial", 16), bg="#faf8ef", fg="#776e65").pack(
                side=tk.LEFT)
            delete_button = tk.Button(frame, text="Delete", command=lambda name=name: self.delete_high_score(name),
                                      font=("Arial", 12), bg="#f44336", fg="white", relief=tk.FLAT)
            delete_button.pack(side=tk.RIGHT)
        tk.Button(score_window, text="Add Score", command=lambda: self.add_high_score(score_window), font=("Arial", 16),
                  bg="#8f7a66", fg="white", activebackground="#d6ccc6").pack(pady=10)

    def delete_high_score(self, name):
        """删除某个玩家的高分记录"""
        score_list = self.load_high_scores()
        score_list = [item for item in score_list if item[0] != name]
        self.save_high_scores(score_list)
        self.show_high_scores()

    def load_high_scores(self):
        """加载高分记录"""
        if os.path.exists("high_scores.json"):
            with open("high_scores.json", "r") as f:
                return json.load(f)
        return []

    def save_high_scores(self, scores):
        """保存高分记录"""
        with open("high_scores.json", "w") as f:
            json.dump(scores, f)

    def add_high_score(self, score_window):
        """添加新的高分记录"""
        def submit_score():
            name = entry.get()
            if name:
                score_list = self.load_high_scores()
                exists = False
                for i, (n, sc) in enumerate(score_list):
                    if n == name:  # 如果名称已存在则更新分数
                        score_list[i][1] = max(sc, self.score)
                        exists = True
                        break
                if not exists:
                    score_list.append([name, self.score])  # 新增高分
                score_list.sort(key=lambda x: x[1], reverse=True)  # 根据分数排序
                score_list = score_list[:10]  # 只保留前10名
                self.save_high_scores(score_list)
                score_window.destroy()  # 关闭添加窗口
                self.show_high_scores()  # 更新高分显示
        # 弹出输入窗口
        entry_window = tk.Toplevel(score_window)
        entry_window.configure(bg="#faf8ef")
        tk.Label(entry_window, text="Enter Your Name:", bg="#faf8ef", fg="#776e65", font=("Arial", 16)).pack()
        entry = tk.Entry(entry_window, font=("Arial", 16))
        entry.pack(padx=10, pady=10)
        tk.Button(entry_window, text="Submit", command=submit_score, font=("Arial", 16),
                  bg="#8f7a66", fg="white", activebackground="#d6ccc6").pack()

if __name__ == "__main__":
    root = tk.Tk()
    game = Game2048(root)
    root.mainloop()

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Wireshark常用功能使用说明

此处用于记录下本人所使用 wireshark 所可能用到的小技巧。Wireshark是一款强大的数据包分析工具&#xff0c;此处仅介绍常用功能。 Wireshark常用功能使用说明 1.相关介绍1.1.工具栏功能介绍1.1.1.时间戳/分组列表概况等设置 1.2.Windows抓包 2.wireshark过滤器规则2.1.wiresh…

像素流送api ue多人访问需要什么显卡服务器

关于像素流送UE推流&#xff0c;在之前的文章里其实小芹和大家聊过很多&#xff0c;不过今天偶然搜索发现还是有很多小伙伴&#xff0c;在搜索像素流送相关的问题&#xff0c;搜索引擎给的提示有这些。当然这些都是比较短的词汇&#xff0c;可能每个人真正遇到的问题和想获取的…

基于Vue3+Element Plus 实现多表单校验

使用场景 表单校验在日常的开发需求中是一种很常见的需求&#xff0c;通常在提交表单发起请求前校验用户输入是否符合规则&#xff0c;通常只需formRef.value.validate()即可校验&#xff0c;但是&#xff0c;例如一些多步骤表单、动态表单、以及不同的用户角色可能看到不同的表…

ONVIF协议网络摄像机客户端使用gsoap获取RTSP流地址GStreamer拉流播放

什么是ONVIF协议 ONVIF&#xff08;开放式网络视频接口论坛&#xff09;是一个全球性的开放式行业论坛&#xff0c;旨在促进开发和使用基于物理IP的安全产品接口的全球开放标准。 ONVIF规范的目标是建立一个网络视频框架协议&#xff0c;使不同厂商生产的网络视频产品完全互通。…

【Datawhale组队学习】模型减肥秘籍:模型压缩技术6——项目实践

NNI (Neural Network Intelligence) 是由微软开发的一个开源自动化机器学习&#xff08;AutoML&#xff09;库&#xff0c;用于帮助研究人员和开发人员高效地进行机器学习实验。它提供了一套丰富的工具来进行模型调优、神经网络架构搜索、模型压缩以及自动化的超参数搜索。 1…

通讯专题4.1——CAN通信之计算机网络与现场总线

从通讯专题4开始&#xff0c;来学习CAN总线的内容。 为了更好的学习CAN&#xff0c;先从计算机网络与现场总线开始了解。 1 计算机网络体系的结构 在我们生活当中&#xff0c;有许多的网络&#xff0c;如交通网&#xff08;铁路、公路等&#xff09;、通信网&#xff08;电信、…

【51单片机】程序实验910.直流电机-步进电机

主要参考学习资料&#xff1a;B站【普中官方】51单片机手把手教学视频 前置知识&#xff1a;C语言 单片机套装&#xff1a;普中STC51单片机开发板A4标准版套餐7 码字不易&#xff0c;求点赞收藏加关注(•ω•̥) 有问题欢迎评论区讨论~ 目录 程序实验9&10.直流电机-步进电机…

Qt支持RKMPP硬解的视频监控系统/性能卓越界面精美/实时性好延迟低/录像存储和回放/云台控制

一、前言 之前做的监控系统&#xff0c;已经实现了在windows上硬解码比如dxva2和d3d11va&#xff0c;后续又增加了linux上的硬解vdpau的支持&#xff0c;这几种方式都是跨系统的硬解实现方案&#xff0c;也是就是如果都是windows系统&#xff0c;无论X86还是ARM都通用&#xf…

Web API基本认知

作用和分类 作用&#xff1a;就是使用JS去操作html和浏览器 分类&#xff1a;DOM&#xff08;文档对象模型&#xff09;、BOM&#xff08;浏览器对象模型&#xff09; 什么是DOM DOM&#xff08;Document Object Model ——文档对象模型&#xff09;是用来呈现以及与任意 HTM…

Linux——自定义简单shell

shell 自定义shell目标普通命令和内建命令&#xff08;补充&#xff09; shell实现实现原理实现代码 自定义shell 目标 能处理普通命令能处理内建命令要能帮助我们理解内建命令/本地变量/环境变量这些概念理解shell的运行 普通命令和内建命令&#xff08;补充&#xff09; …

智能桥梁安全运行监测系统守护桥梁安全卫士

一、方案背景 桥梁作为交通基础设施中不可或缺的重要组成部分&#xff0c;其安全稳定的运行直接关联到广大人民群众的生命财产安全以及整个社会的稳定与和谐。桥梁不仅是连接两地的通道&#xff0c;更是经济发展和社会进步的重要纽带。为了确保桥梁的安全运行&#xff0c;桥梁安…

【Python网络爬虫笔记】5-(Request 带参数的get请求) 爬取豆瓣电影排行信息

目录 1.抓包工具查看网站信息2.代码实现3.运行结果 1.抓包工具查看网站信息 请求路径 url:https://movie.douban.com/typerank请求参数 页面往下拉&#xff0c;出现新的请求结果&#xff0c;参数start更新&#xff0c;每次刷新出20条新的电影数据 2.代码实现 # 使用网络爬…

新质驱动·科东软件受邀出席2024智能网联+低空经济暨第二届湾区汽车T9+N闭门会议

为推进广东省加快发展新质生产力&#xff0c;贯彻落实“百县千镇万村高质量发展工程”&#xff0c;推动韶关市新丰县智能网联新能源汽车、低空经济与数字技术的创新与发展&#xff0c;充分发挥湾区汽车产业链头部企业的带动作用。韶关市指导、珠三角湾区智能网联新能源汽车产业…

C#使用ExcelDataReader读取Xlsx文件为DataTable对象

创建控制台项目 在NuGet中安装ExcelDataReader.DataSet 3.7.0 创建一个xlsx文件 测试代码 读取xlsx文件内容&#xff0c;为一个DataTable对象。 读取xlsx时&#xff0c;xlsx文件不能被其他软件打开&#xff0c;否则会报“进程无法访问此文件”的错。 using ExcelDataRead…

“harmony”整合不同平台的单细胞数据之旅

其实在Seurat v3官方网站的Vignettes中就曾见过该算法&#xff0c;但并没有太多关注&#xff0c;直到看了北大张泽民团队在2019年10月31日发表于Cell的《Landscap and Dynamics of Single Immune Cells in Hepatocellular Carcinoma》&#xff0c;为了同时整合两类数据&#xf…

智慧银行反欺诈大数据管控平台方案(一)

智慧银行反欺诈大数据管控平台建设方案的核心在于通过整合先进的大数据技术和深度学习算法&#xff0c;打造一个全面、智能且实时的反欺诈系统&#xff0c;以有效识别、预防和应对各类金融欺诈行为。该方案涵盖数据采集、存储、处理和分析的全流程&#xff0c;利用多元化的数据…

基于 JNI + Rust 实现一种高性能 Excel 导出方案(上篇)

每个不曾起舞的日子,都是对生命的辜负。 ——尼采 一、背景:Web 导出 Excel 的场景 Web 导出 Excel 功能在数据处理、分析和共享方面提供了极大的便利,是许多 Web 应用程序中的重要功能。以下是一些典型的场景: 数据报表导出:在企业管理系统(如ERP、CRM)中,用户经常需…

使用 Tkinter 创建一个简单的 GUI 应用程序来合并视频和音频文件

使用 Tkinter 创建一个简单的 GUI 应用程序来合并视频和音频文件 Python 是一门强大的编程语言&#xff0c;它不仅可以用于数据处理、自动化脚本&#xff0c;还可以用于创建图形用户界面 (GUI) 应用程序。在本教程中&#xff0c;我们将使用 Python 的标准库模块 tkinter 创建一…

「Mac畅玩鸿蒙与硬件35」UI互动应用篇12 - 简易日历

本篇将带你实现一个简易日历应用&#xff0c;显示当前月份的日期&#xff0c;并支持选择特定日期的功能。用户可以通过点击日期高亮选中&#xff0c;还可以切换上下月份&#xff0c;体验动态界面的交互效果。 关键词 UI互动应用简易日历动态界面状态管理用户交互 一、功能说明…

江协科技最新OLED保姆级移植hal库

江协科技最新OLED移植到hal库保姆级步骤 源码工程存档 工程和源码下载(密码 1i8y) 原因 江协科技的开源OLED封装的非常完美, 可以满足我们日常的大部分开发, 如果可以用在hal库 ,将是如虎添翼, 为我们开发调试又增加一个新的瑞士军刀, 所以我们接下来手把手的去官网移植源码…