当前位置: 首页 > news >正文

Qt 音乐播放器项目

具体代码见:https://gitee.com/Suinnnnnn/MusicPlayer

文章目录

  • 0. 预备
  • 1. 界面
    • 1.1 各部位长度
    • 1.2 ui文件
    • 1.3 窗口前置设置
    • 1.4 设置QSS
  • 2. 自定义控件
    • 2.1 按钮
    • 2.2 推荐页面
    • 2.3 CommonPage
    • 2.4 滑杆
  • 3. 音乐管理
  • 4. 歌词界面
    • 4.1 ui文件
    • 4.2 LrcPage.h文件
  • 5. 音乐播放控制 + 持久化控制

0. 预备

各个类的作用:

ButtonForm: 自定义了按钮,其包含了图片,文字和动画效果
CommonPage:自定义页面,被“我的”之后的三个页面使用
CommonPageItem:歌曲的每一行就是一个该类的对象,包括编号,歌曲名,专辑名,时间,是否喜欢
CommonSlider:音乐进度条使用,表明当前播放到哪里,支持seek功能
CustomPlaylist:简单实现了在Qt6中删除的QMediaPlaylist
LrcPage:歌词页面
Music:用户直接交互的页面
MusicInfo:保存歌曲信息的类
MusicList:组织MusicInfo的类
RecBoxItemRecommendBox中的一个个单元
RecommendBox:推荐界面的简单实现
VolumBox:音量控制条,支持seek功能

1. 界面

1.1 各部位长度

image-20250303202055668

1.2 ui文件

image-20250303202127812

image-20250303202311424

1.3 窗口前置设置

music.cpp如下

#include "music.h"
#include <QGraphicsDropShadowEffect>
#include <QMouseEvent>
#include "ui_music.h"Music::Music(QWidget* parent): QWidget(parent), ui(new Ui::Music)
{ui->setupUi(this);initUI();
}void Music::initUI()
{// 设置无边框this->setWindowFlag(Qt::FramelessWindowHint);// 设置窗体透明,不然看不到阴影效果this->setAttribute(Qt::WA_TranslucentBackground);// 添加阴影效果QGraphicsDropShadowEffect* shadowEffect = new QGraphicsDropShadowEffect(this);shadowEffect->setOffset(0, 0);           // 设置阴影距离shadowEffect->setColor(QColor(0, 0, 0)); // 设置阴影颜色shadowEffect->setBlurRadius(100);         // 设置阴影模糊半径this->setGraphicsEffect(shadowEffect);   // 给 QWidget设置阴影
}void Music::mousePressEvent(QMouseEvent* event)
{// 如果按下左键,记录dragPosif (event->button() == Qt::LeftButton) {QPoint p1     = event->globalPosition().toPoint();QPoint p2     = geometry().topLeft();this->dragPos = p1 - p2;// qDebug() << dragPos;return;}// 其余事件让父类处理QWidget::mousePressEvent(event);
}void Music::mouseMoveEvent(QMouseEvent* event)
{// 如果按下左键并移动,那么就让窗口移动if (event->buttons() == Qt::LeftButton) {QPoint p1 = event->globalPosition().toPoint();QPoint p2 = this->dragPos;this->move(p1 - p2);// qDebug() << "dragPos: " << p2 << "\nglobalPos: " << p1;return;}// 其余事件让父类处理QWidget::mouseMoveEvent(event);
}Music::~Music()
{// qDebug() << "Music::~Music() called";delete ui;
}void Music::on_close_btn_clicked()
{// 关闭窗口this->close();
}

1.4 设置QSS

widget.ui中删除部分空间的背景颜色,设置QSS。

2. 自定义控件

2.1 按钮

自定义一个ButtonForm,由几个QWidgetQLabel组成
image-20250307223547243

buttonform.h

#ifndef BUTTONFORM_H
#define BUTTONFORM_H#include <QFrame>
#include <QPropertyAnimation>
namespace Ui
{
class ButtonForm;
}class ButtonForm : public QFrame
{Q_OBJECT
public:explicit ButtonForm(QWidget* parent = nullptr);void set_id_and_icon_and_text(int id, const QString& icon, const QString& text);void clear_backgrond_color() const;int  get_page_id() const;void show_animation();void hide_animation();~ButtonForm();
protected:void mousePressEvent(QMouseEvent* event);private:void                set_animation_and_start(QPropertyAnimation* animation, int duration,QRect rect1, QRect rect2, QRect rect3, int loopCount);Ui::ButtonForm*     ui;int                 pageID;          // 当前页面的ID, 用于翻页QPropertyAnimation* line1_animation; // 动画QPropertyAnimation* line2_animation;QPropertyAnimation* line3_animation;QPropertyAnimation* line4_animation;QPropertyAnimation* line5_animation;
signals:void clicked(int pageID);
};#endif // BUTTONFORM_H

接着将music.ui中的左侧QWidget替换为ButtonForm

运行结果如下,点击不同的按钮可以跳转到不同的QWidget,且按钮有动画效果

image-20250313214533199

2.2 推荐页面

music.ui中的recommend_page下添加一个QScrollArea类型的scrollArea,里面有三个QLabel和两个RecommendBox

image-20250313214119841

RecommendBox.ui如下

image-20250313214155057

RecommendBox.h

#ifndef RECOMMENDBOX_H
#define RECOMMENDBOX_H#include <qjsonarray.h>
#include <QWidget>namespace Ui
{
class RecommendBox;
}class RecommendBox : public QWidget
{Q_OBJECTpublic:explicit RecommendBox(QWidget* parent = nullptr);void init_rec_box(QJsonArray pics);void set_col_and_row(int row, int col);~RecommendBox();private slots:void on_left_btn_clicked();void on_right_btn_clicked();
private:void              add_rec_item();void              del_rec_item();Ui::RecommendBox* ui;int               row           = 2;int               column        = 5;int               current_group = 0; // 当前是第几组int               group_count;       // 一共有多少组QJsonArray        pics_path_and_text;
};#endif // RECOMMENDBOX_H

RecBoxItem.ui如下

image-20250313214254346

RecBoxItem.h如下

#ifndef RECBOXITEM_H
#define RECBOXITEM_H#include <QPropertyAnimation>
#include <QWidget>namespace Ui
{
class RecBoxItem;
}class RecBoxItem : public QWidget
{Q_OBJECTpublic:explicit RecBoxItem(QWidget* parent = nullptr);bool eventFilter(QObject* watched, QEvent* event);void set_icon_and_text(const QString& icon, const QString& text);~RecBoxItem();private:Ui::RecBoxItem*                                                         ui;std::function<void(QPropertyAnimation*, int, QRect, QRect, QRect, int)> set_animation_and_start;
};#endif // RECBOXITEM_H

运行结果如下,支持换页,而且选中图片会有动画效果

image-20250313214420275

2.3 CommonPage

由于需要上传文件,所以现在把之前的我的播客改为上传音乐

image-20250318201535927

CommonPage被播客, 我喜欢, 最近播放, 上传音乐所使用。
下面是CommonPage.ui

image-20250318201704598

下面是CommonPage.h(目前)

#ifndef COMMONPAGE_H
#define COMMONPAGE_H#include <QFrame>namespace Ui
{
class CommonPage;
}class CommonPage : public QFrame
{Q_OBJECTpublic:explicit CommonPage(QWidget* parent = nullptr);void init_my_like();void init_podcast();void init_recent_play();void init_upload_music();~CommonPage();
private:void            set_podcast();void            reset_up_widget(const QString& title = "xxx");Ui::CommonPage* ui;
};#endif // COMMONPAGE_H

CommonPage使用了CommonPageItem,下面是CommonPageItem.ui

image-20250318201815958

CommonPageItem.h如下

#ifndef COMMONPAGEITEM_H
#define COMMONPAGEITEM_H
#include <QFrame>namespace Ui
{
class CommonPageItem;
}class CommonPageItem : public QFrame
{Q_OBJECTpublic:explicit CommonPageItem(QWidget* parent = nullptr);const QRect& get_page_item_geometry() const;void         set_num(int num);void         enterEvent(QEnterEvent* event);void         leaveEvent(QEvent* event);void         mouseDoubleClickEvent(QMouseEvent* event);~CommonPageItem();private:void                set_background_color(const QString& color);bool                is_played() const;int                 play_num = -1;Ui::CommonPageItem* ui;
};#endif // COMMONPAGEITEM_H

2.4 滑杆

CommonSlider.ui,音乐进度条使用

image-20250318202343565

CommonSlider.h

#ifndef COMMONSLIDER_H
#define COMMONSLIDER_H#include <QFrame>namespace Ui
{
class CommonSlider;
}/* 愿意是想让进度条和音量条都用该类,后来发现不如再写一个类。此类仅用于进度条 */
class CommonSlider : public QFrame
{Q_OBJECTpublic:explicit CommonSlider(QWidget* parent = nullptr);void init_progress_bar();void init_volume_btn();~CommonSlider();private:Ui::CommonSlider* ui;
};#endif // COMMONSLIDER_H

VolumeBox.ui,音量按钮使用

image-20250318202432773

VolumeBox.h

#ifndef VOLUMEBOX_H
#define VOLUMEBOX_H#include <QFrame>namespace Ui
{
class VolumeBox;
}class VolumeBox : public QFrame
{Q_OBJECTpublic:explicit VolumeBox(QWidget* parent = nullptr);~VolumeBox();
private:Ui::VolumeBox* ui;
};#endif // VOLUMEBOX_H

music.cpp中给音量按钮添加事件过滤器

bool Music::eventFilter(QObject* obj, QEvent* event)
{if (obj == ui->play_volume_btn || obj == volume_box) {if (event->type() == QEvent::Enter) {// 鼠标进入时显示 volume_boxQPoint btnPos    = ui->play_volume_btn->mapToGlobal(QPoint(0, 0)); // 获取全局坐标QPoint targetPos = btnPos - QPoint(10, volume_box->height());      // 按钮上方volume_box->move(targetPos);volume_box->show();} else if (event->type() == QEvent::Leave) {// 鼠标离开时隐藏 VolumeBox (如果超过了300ms)hide_timer->start(300);}}return QWidget::eventFilter(obj, event);
}

3. 音乐管理

设置此按钮的槽函数

image-20250318202730525

点击后需要添加我们选中的文件,使用QFileDialog。使用MusicInfo类保存所有音乐的信息。使用MusicList类来管理这些Music

MusicInfo.h,储存音乐信息

#ifndef MUSICINFO_H
#define MUSICINFO_H#include <QString>
#include <QUrl>
#include <QUuid>class MusicInfo
{
public:MusicInfo(const QUrl& url);// 禁止拷贝(根据需要实现移动语义)MusicInfo(const MusicInfo&)            = delete;MusicInfo& operator=(const MusicInfo&) = delete;/* 必须声明移动构造函数,作用如下* 1. 明确告知编译器生成移动构造函数* 2. 允许容器使用移动语义操作对象* 3. 保留类的不可拷贝特性* */MusicInfo(MusicInfo&&)            = default;MusicInfo& operator=(MusicInfo&&) = default;bool       is_valid();void       parse_metadata();QUuid      getUuid() const;bool    getIs_like() const;void    setIs_like(bool newIs_like);bool    getIs_recent_play() const;void    setIs_recent_play(bool newIs_recent_play);bool    getIs_valid_flag() const;void    setIs_valid_flag(bool newIs_valid_flag);QString getMusic_name() const;QString getAlbum_name() const;qint64  getMusic_time() const;private:void    check_valid();QUuid   uuid;                   // uuid, 防止重复QUrl    url;                    // 歌曲的URLQString music_name;             // 音乐名称QString album_name;             // 专辑名称qint64  music_time;             // 音乐持续时间(ms)bool    is_like        = false; // 是否喜欢bool    is_recent_play = false; // 是否是最近播放bool    is_valid_flag  = false; // 是否是音频文件
};#endif                              // MUSICINFO_H

MusicList.h,管理一个个MusicInfo

#ifndef MUSICINFO_H
#define MUSICINFO_H#include <QString>
#include <QUrl>
#include <QUuid>class MusicInfo
{
public:MusicInfo(const QUrl& url);// 禁止拷贝(根据需要实现移动语义)MusicInfo(const MusicInfo&)            = delete;MusicInfo& operator=(const MusicInfo&) = delete;/* 必须声明移动构造函数,作用如下* 1. 明确告知编译器生成移动构造函数* 2. 允许容器使用移动语义操作对象* 3. 保留类的不可拷贝特性* */MusicInfo(MusicInfo&&)            = default;MusicInfo& operator=(MusicInfo&&) = default;bool       is_valid();void       parse_metadata();QUuid      getUuid() const;bool    getIs_like() const;void    setIs_like(bool newIs_like);bool    getIs_recent_play() const;void    setIs_recent_play(bool newIs_recent_play);bool    getIs_valid_flag() const;void    setIs_valid_flag(bool newIs_valid_flag);QString getMusic_name() const;QString getAlbum_name() const;qint64  getMusic_time() const;private:void    check_valid();QUuid   uuid;                   // uuid, 防止重复QUrl    url;                    // 歌曲的URLQString music_name;             // 音乐名称QString album_name;             // 专辑名称qint64  music_time;             // 音乐持续时间(ms)bool    is_like        = false; // 是否喜欢bool    is_recent_play = false; // 是否是最近播放bool    is_valid_flag  = false; // 是否是音频文件
};#endif                              // MUSICINFO_H

Music.h中增加处理点击爱心按钮的槽函数

void handle_item_like_btn_clicked(bool is_like, const QUuid& uuid);

4. 歌词界面

解析.lrc文件

4.1 ui文件

image-20250406194553897

4.2 LrcPage.h文件

#ifndef LRCPAGE_H
#define LRCPAGE_H
#include <QFrame>
#include <QPropertyAnimation>namespace Ui
{
class LrcPage;
}// 歌词的一行
struct LyricLine {LyricLine(qint64 time_p, QString text_p): time(time_p), text(text_p){}qint64  time; // 时间(ms)QString text; // 歌词
};class LrcPage : public QFrame
{Q_OBJECTpublic:explicit LrcPage(QWidget* parent = nullptr);bool    parse_lrc_file(const QString& lrc_filename);void    push_line_to_lrc_vector(qint64 time, QString text);QString get_lrc_filename_by_url(const QUrl& url);void    set_ui_label(qint64 time);void    set_name_and_singer(const QString& music, const QString& singer);void    clear_lyric_lines();~LrcPage();
private slots:void on_quit_clicked();
private:int                 get_lyric_lines_index_by_time(qint64 time);QString             get_lyric_lines_line_by_index(int index);Ui::LrcPage*        ui;QPropertyAnimation* lrc_animation; // 歌词界面隐藏动画QVector<LyricLine>  lyric_lines;   // 歌词的所有内容,由一行行的结构体组成
};#endif                                 // LRCPAGE_H

5. 音乐播放控制 + 持久化控制

使用QMediaPlayer类,由于Qt6中删除了QPlayList类,所以我自定义了一个CustomPlayList

#ifndef CUSTOMPLAYLIST_H
#define CUSTOMPLAYLIST_H#include <QList>
#include <QMediaPlayer>
#include <QObject>
#include <QRandomGenerator>
#include <QUrl>class CustomPlaylist : public QObject
{Q_OBJECTpublic:enum PlaybackMode {Sequential, // 顺序播放SingleLoop, // 单曲循环播放Random      // 随机播放};Q_ENUM(PlaybackMode)explicit CustomPlaylist(QMediaPlayer* player, QObject* parent = nullptr);// 基本操作void addMedia(const QUrl& url);void removeMedia(int index);void clear();void next();void previous();void setCurrentIndex(int index);// 获取信息int  currentIndex() const;QUrl currentMedia() const;int  mediaCount() const;// 播放模式PlaybackMode playbackMode() const;void         setPlaybackMode(PlaybackMode mode);signals:void currentIndexChanged(int index);void mediaAdded(int index);void mediaRemoved(int index);void playbackModeChanged(PlaybackMode mode);private slots:void handleMediaStatusChanged(QMediaPlayer::MediaStatus status);private:QList<QUrl>   m_mediaList;         // 存储媒体项int           m_currentIndex = -1; // 当前播放索引PlaybackMode  m_playbackMode = Sequential;QMediaPlayer* m_player;            // 关联的 QMediaPlayerQList<int>    m_randomOrder;       // 随机播放顺序缓存void updateRandomOrder();          // 更新随机播放顺序int  getNextIndex() const;         // 根据模式获取下一个索引int  getPreviousIndex() const;     // 根据模式获取上一个索引
};
#endif                                 // CUSTOMPLAYLIST_H

使用QSQLITE数据库,用于持久化操作,下面是music.h文件

#ifndef MUSIC_H
#define MUSIC_H#include <QAudioOutput>
#include <QJsonArray>
#include <QMediaPlayer>
#include <QPropertyAnimation>
#include <QSqlDatabase>
#include <QWidget>
#include "CommonPage.h"
#include "CustomPlaylist.h"
#include "LrcPage.h"
#include "VolumeBox.h"QT_BEGIN_NAMESPACE
namespace Ui
{
class Music;
}
QT_END_NAMESPACEclass Music : public QWidget
{Q_OBJECTpublic:Music(QWidget* parent = nullptr);void       initUI();void       initPlayer();void       initStaticToolTip();void       initSqlLite();void       initMusicList();void       connect_signals_and_slots();void       mousePressEvent(QMouseEvent* event);void       mouseMoveEvent(QMouseEvent* event);bool       eventFilter(QObject* obj, QEvent* event);void       play_music_from_index(CommonPage* page, int index);QJsonArray get_random_recommend_pic() const;~Music();
private slots:// 形如on_xxx是ui文件生成的, 其余是自己写的void handle_button_form_clicked(int pageID);void handle_item_like_btn_clicked(bool is_like, const QUuid& uuid);void handle_upload_music();void handle_play_state_changed(QMediaPlayer::PlaybackState new_state);void handle_play_mode_changed(CustomPlaylist::PlaybackMode mode);void handle_play_all_music_btn_clicked(CommonPage* page);void handle_double_clicked_song(CommonPage* page, int index);void handle_current_index_changed(int new_index);void handle_volume_changed(int volume);void handle_duration_changed(qint64 duration);void handle_position_changed(qint64 duration);void handle_slider_pos_changed(double ratio);void handle_meta_data_changed();void on_close_btn_clicked();void on_stop_btn_clicked();void on_next_song_btn_clicked();void on_prev_song_btn_clicked();void on_play_mode_btn_clicked();void on_play_volume_btn_clicked();void on_my_like_btn_clicked();void on_lrc_btn_clicked();void on_music_pic_btn_clicked();void on_min_btn_clicked();
private:void                      hide_volume_box();static QString            transform_million_second(qint64 msecond);void                      set_like_btn_icon(bool is_like);MusicList::const_iterator get_now_play_music_info_by_index(int index);void                      quit_progress();
private:Ui::Music* ui;// 由于窗口没有了默认边框,所以要想移动,需要有该属性,其值为 全局的鼠标位置-widget左上位置QPoint              dragPos;VolumeBox*          volume_box;QTimer*             hide_timer;QMediaPlayer*       player;CustomPlaylist*     play_list;QAudioOutput*       audio_output;CommonPage*         play_page;       // 当前播放bool                is_mute = false; // 是否静音, false表示没被静音qint64              total_duration;  // 当前音乐的总时长LrcPage*            lrc_page;        // 歌词页面QPropertyAnimation* lrc_animation;   // 歌词界面显示动画QSqlDatabase        db;              // 数据库驱动
};
#endif                                   // MUSIC_H

相关文章:

Qt 音乐播放器项目

具体代码见&#xff1a;https://gitee.com/Suinnnnnn/MusicPlayer 文章目录 0. 预备1. 界面1.1 各部位长度1.2 ui文件1.3 窗口前置设置1.4 设置QSS 2. 自定义控件2.1 按钮2.2 推荐页面2.3 CommonPage2.4 滑杆 3. 音乐管理4. 歌词界面4.1 ui文件4.2 LrcPage.h文件 5. 音乐播放控…...

初识数据结构——Java集合框架解析:List与ArrayList的完美结合

&#x1f4da; Java集合框架解析&#xff1a;List与ArrayList的完美结合 &#x1f31f; 前言&#xff1a;为什么我们需要List和ArrayList&#xff1f; 在日常开发中&#xff0c;我们经常需要处理一组数据。想象一下&#xff0c;如果你要管理一个班级的学生名单&#xff0c;或…...

LightRAG实战:轻松构建知识图谱,破解传统RAG多跳推理难题

作者&#xff1a;后端小肥肠 &#x1f34a; 有疑问可私信或评论区联系我。 &#x1f951; 创作不易未经允许严禁转载。 姊妹篇&#xff1a; 2025防失业预警&#xff1a;不会用DeepSeek-RAG建知识库的人正在被淘汰_deepseek-embedding-CSDN博客 从PDF到精准答案&#xff1a;Coze…...

Hyperlane框架全面详解与应用指南 [特殊字符][特殊字符][特殊字符]

Hyperlane框架全面详解与应用指南 &#x1f680;&#x1f680;&#x1f680; &#x1f4da; 前言 欢迎来到Hyperlane框架的全面详解与应用指南&#xff01;&#x1f389;&#x1f389;&#x1f389; 本文档旨在为开发者提供一个全面、详尽的Hyperlane框架使用指南&#xff0c…...

使用LVS的 NAT 模式实现 3 台RS的轮询访问

题目 使用LVS的 NAT 模式实现 3 台RS的轮询访问。IP地址和主机自己规划。 -i— turn&#xff0c;-g——DR模式&#xff0c;-m——NAT模式 节点规划 仅主机网段&#xff1a;192.168.216.0/24 NAT网段&#xff1a;192.168.88.0/24 主机角色系统网络ipclientclientredhat9.5仅…...

BGP路由协议之属性4

MED 多出口鉴别器 可选非过渡属性 EBGP 的邻居 Cost 开销值&#xff0c;控制如何进入 AS。越小越优。继承 IGP 的开销值&#xff0c;默认 0 MED(Multi-Exit Discriminator&#xff0c;多出口鉴别器)是可选非过属性&#xff0c;是一种度量值用于向外部对等体指出进入本 AS 的首…...

数据库的操作

1.创建数据库 CREATE DATABASE [IF NOT EXISTS] db_name [create_specification [,create_specification] ...]create_specification: [DEFAULT] CHARACTER SET charset_name [DEFAULT] COLLATE collation_name 大写的表示关键字。[]是可选项。CHARACTER SET&#xff1a;指定…...

【愚公系列】《高效使用DeepSeek》055-可靠性评估与提升

🌟【技术大咖愚公搬代码:全栈专家的成长之路,你关注的宝藏博主在这里!】🌟 📣开发者圈持续输出高质量干货的"愚公精神"践行者——全网百万开发者都在追更的顶级技术博主! 👉 江湖人称"愚公搬代码",用七年如一日的精神深耕技术领域,以"…...

记录clickhouse记录一次性能优化,从60s到1s

文章目录 问题表结构类似如下分析第一步调整第一步观察多磁盘读继续观察sql 问题 一个查询接口&#xff0c;涉及多个clickhouse 查询&#xff0c;查询用时一下变成要60s 表结构类似如下 CREATE TABLE demo.test_local (id UUID,date DateTime,type String ) ENGINE Replic…...

二叉树的层序遍历

102. Binary Tree Level Order Traversal 广度优先搜索 将每个结点的层号记录下。 /*** Definition for a binary tree node.* struct TreeNode {* int val;* TreeNode *left;* TreeNode *right;* TreeNode() : val(0), left(nullptr), right(nullptr) {}* …...

嵌入式硬件篇---TOF陀螺仪SPI液晶屏

文章目录 前言1. TOF传感器&#xff08;Time of Flight&#xff09;原理STM32使用方法硬件连接SDASCLVCC\GND 软件配置初始化I2C外设库函数驱动&#xff1a;读取数据 2. 陀螺仪&#xff08;如MPU6050&#xff09;原理STM32使用方法硬件连接SDA/SCLINTVCC/GND 软件配置初始化I2C…...

OpenCV 在树莓派上进行实时人脸检测

这段 Python 代码借助 OpenCV 库实现了在树莓派上进行实时人脸检测的功能。它会开启摄像头捕获视频帧&#xff0c;在每一帧里检测人脸并以矩形框标记出来&#xff0c;同时在画面上显示帧率&#xff08;FPS&#xff09;。 依赖库 cv2&#xff1a;OpenCV 库&#xff0c;用于计算…...

55.跳跃游戏

​​题目来源&#xff1a; leetcode题目&#xff0c;网址&#xff1a;55. 跳跃游戏 - 力扣&#xff08;LeetCode&#xff09; 解题思路&#xff1a; 遍历数组&#xff0c;若当前节点可达&#xff0c;更新可到达的最远距离&#xff0c;否则返回false。若可遍历整个数组&#xf…...

awk 实现listagg ,count 功能

awk命令实现分组统计 测试数据 ABC a1 ABC a2 ABC a3 ABD c1 ABD c2 分组统计 abc a1,a2,a3 3 abd c1,c2 awk 命令 awk {arr[$1]arr[$1] ? arr[$1] "," $2 : $2; count[$1]} END{for (i in arr) print tolower(i), arr[i], count[i]} group_…...

瑞萨RA4M2使用心得-GPIO输出

目录 一、新建项目 二、图形化开发 1.初始化IO 2.界面介绍 3.代码编写 4.所有内部函数的封装位置 5.LED闪烁函数编写 三.debug运行 总结 环境&#xff1a; 开发板&#xff1a;RA-Eco-RA4M2-100PIN-V1.0 IDE&#xff1a;e2 studio 一、新建项目 正常操作&#xff0c;下…...

uniapp微信小程序引入vant组件库

1、首先要有uniapp项目&#xff0c;根据vant官方文档使用yarn或npm安装依赖&#xff1a; 1、 yarn init 或 npm init2、 # 通过 npm 安装npm i vant/weapp -S --production# 通过 yarn 安装yarn add vant/weapp --production# 安装 0.x 版本npm i vant-weapp -S --production …...

COZE通关指南:工作流与插件开发

前言 本文隶属于专栏《AI Agent 通关指南》,该专栏为笔者原创,引用请注明来源,不足和错误之处请在评论区帮忙指出,谢谢! 本专栏目录结构和参考文献请见《AI Agent 通关指南》 正文 1. 平台基础介绍 🌟 1.1 COZE平台概述 COZE平台(coze.cn)是一个强大的AI应用开发平台…...

在Unity中,如果物体上的脚本丢失,可以通过编写一个自定义编辑器脚本来查找并删除这些丢失的组件

在Unity中&#xff0c;如果物体上的脚本丢失&#xff0c;可以通过编写一个自定义编辑器脚本来查找并删除这些丢失的组件。以下是一个示例脚本&#xff0c;它可以帮助你一键检索场景中所有丢失脚本的物体&#xff0c;并删除这些丢失的组件。 步骤&#xff1a; 创建编辑器脚本&a…...

青少年编程与数学 02-016 Python数据结构与算法 04课题、栈与队列

青少年编程与数学 02-016 Python数据结构与算法 04课题、栈与队列 一、栈1. 栈的定义2. 栈的特点3. 栈的基本操作示例 4. 栈的实现&#xff08;1&#xff09;数组实现&#xff08;2&#xff09;链表实现 5. 栈的应用&#xff08;1&#xff09;函数调用&#xff08;2&#xff09…...

Lucene.Net全文搜索引擎:架构解析与全流程实战指南

文章目录 引言&#xff1a;为什么选择Lucene.Net&#xff1f;一、Lucene.Net核心架构剖析1.1 模块化设计 二、Lucene.Net索引原理揭秘2.1 倒排索引&#xff1a;搜索的基石2.2 段&#xff08;Segment&#xff09;机制 三、全流程实战&#xff1a;从0到1构建搜索引擎3.1 环境准备…...

OpenSceneGraph 中的 LOD详解

LOD (Level of Detail&#xff0c;细节层次) 是3D图形中一种重要的优化技术&#xff0c;OpenSceneGraph 通过 osg::LOD 类提供了完整的LOD支持。 一、LOD 基本概念 1. 什么是LOD 核心思想&#xff1a;根据物体与相机的距离显示不同细节程度的模型 目的&#xff1a;减少远处物…...

程序化广告行业(64/89):AdX/SSP系统广告位设置全解析

程序化广告行业&#xff08;64/89&#xff09;&#xff1a;AdX/SSP系统广告位设置全解析 大家好&#xff01;我一直觉得在技术和营销不断融合的当下&#xff0c;程序化广告领域充满了机遇与挑战。之前和大家分享了程序化广告PDB模式的相关知识&#xff0c;今天想接着和大家一起…...

Pytorch中的计算图(Computational Graph)是什么

&#x1f9e9; 一、什么是计算图&#xff1f; 计算图是一种“有向无环图&#xff08;DAG&#xff09;”&#xff0c;表示变量&#xff08;张量&#xff09;之间的运算关系。 节点&#xff1a;张量或操作&#xff08;如加法、乘法&#xff09;边&#xff1a;数据流&#xff08;即…...

Java 大视界 -- Java 大数据在航天遥测数据分析中的技术突破与应用(177)

&#x1f496;亲爱的朋友们&#xff0c;热烈欢迎来到 青云交的博客&#xff01;能与诸位在此相逢&#xff0c;我倍感荣幸。在这飞速更迭的时代&#xff0c;我们都渴望一方心灵净土&#xff0c;而 我的博客 正是这样温暖的所在。这里为你呈上趣味与实用兼具的知识&#xff0c;也…...

【Linux操作系统——学习笔记三】Linux环境下多级目录构建与管理的命令行实践报告

1.在用户主目录下&#xff0c;使用以下方法新建目录&#xff0c;并显示详细执行过程&#xff1a; &#xff08;1&#xff09;使用绝对路径在当前目录下创建 new_dir目录 &#xff08;2&#xff09;使用相对路径、在当前目录创建dir1、dir2、dir3目录 &#xff08;3&#xff09…...

java.util.Collections中常用api

在Java中&#xff0c;java.util.Collections 是一个工具类&#xff0c;提供了大量静态方法用于操作或返回集合&#xff08;如List、Set、Map等&#xff09;。以下是常用的API分类整理&#xff1a; 1. 排序与顺序操作 sort(List<T> list) 对List进行自然顺序排序&#xff…...

批量将图片统一色调

from PIL import Image, ImageEnhance # 确保导入 ImageEnhance 模块 import osdef adjust_image_tone(image_path, output_path, r_weight1.0, g_weight1.0, b_weight1.0, brightness1.0):"""调整图片的色调、明暗&#xff0c;并进行去图处理。参数:image_pat…...

OCC Shape 操作

#pragma once #include <iostream> #include <string> #include <filesystem> #include <TopoDS_Shape.hxx> #include <string>class GeometryIO { public:// 加载几何模型&#xff1a;支持 .brep, .step/.stp, .iges/.igsstatic TopoDS_Shape L…...

docker的run命令 笔记250406

docker的run命令 笔记250406 Docker 的 run 命令用于创建并启动一个新的容器。它是 Docker 中最常用的命令之一&#xff0c;基本语法为&#xff1a; docker run [OPTIONS] IMAGE [COMMAND] [ARG...]常用选项&#xff08;OPTIONS&#xff09; 参数说明-d 或 --detach后台运行…...

批量将 HTML 转换为 Word/Txt/PDF 等其它格式

HTML是一种超文本标记语言&#xff0c;在进行网页编辑的时候非常常见&#xff0c;我们浏览的网站内容&#xff0c;都可以保存为 html 格式&#xff0c;如果想要将 html 格式的文档转为其它格式&#xff0c;比如 Word、PDF 或者 Txt&#xff0c;我们应该怎么做呢&#xff1f;今天…...

TPS入门DAY02 服务器篇

1.创建空白插件 2.导入在线子系统以及在线steam子系统库 MultiplayerSessions.uplugin MultiplayerSessions.Build.cs 3.创建游戏实例以及初始化会话创建流程 创建会话需要的函数&#xff0c;委托&#xff0c;委托绑定的回调&#xff0c;在线子系统接口绑定某一个委托的控制其…...

C高级,终端操作

核心要点整理 刷题作业 一、基础操作 命令行提示符结构 ubuntuubuntu:~$ 当前用户 | 连接符 | 计算机名 | 当前路径 | 用户权限 用户切换 su 用户名&#xff1a;切换用户sudo passwd 用户名&#xff1a;修改用户密码 常用指令 cd -&#xff1a;返回上一次路径ls&#xff1a;显…...

Lua语言的边缘计算

Lua语言的边缘计算探索 引言 随着物联网&#xff08;IoT&#xff09;、人工智能&#xff08;AI&#xff09;和大数据技术迅速发展&#xff0c;边缘计算作为一种分布式计算架构日益受到重视。其核心理念是将计算和数据存储资源更靠近数据源&#xff0c;以降低延迟、减轻网络负…...

RabbitMQ运维

RabbitMQ运维 一.集群1.简单介绍2.集群的作用 二.搭建集群1.多机多节点搭建步骤 2.单机单节点搭建步骤 3.宕机演示 三.仲裁队列1.简单介绍2.Raft协议Raft基本概念主节点选举选举过程 3.仲裁队列的使用 四.HAProxy负载均衡1.安装HAProxy2.HAProxy的使用 一.集群 1.简单介绍 Ra…...

【ESP32】ESP32物联网应用:MQTT控制与状态监测

ESP32物联网应用&#xff1a;MQTT控制与状态监测 引言 在物联网时代&#xff0c;远程监测和控制设备已经成为现实生活中常见的需求。本文将介绍如何使用ESP32微控制器配合MQTT协议&#xff0c;实现一个简单而强大的物联网应用&#xff1a;远程状态监测和设备控制。我们将以巴…...

如何保证RabbitMQ消息的可靠传输?

在这个图中&#xff0c;消息可能丢失的场景是1&#xff0c;2&#xff0c;3 1.在生产者将消息发送给RabbitMQ的时候&#xff0c;消息到底有没有正确的到达服务器呢&#xff0c;RabbitMQ提供了两种解决方案&#xff1a; a. 通过事务机制实现&#xff08;比较消耗性能&#xff0…...

Redis高可用

主从复制 为什么要主从复制&#xff1f; 由于数据都是存储在一台服务器上&#xff0c;如果出事就完犊子了&#xff0c;比如&#xff1a; 如果服务器发生了宕机&#xff0c;由于数据恢复是需要点时间&#xff0c;那么这个期间是无法服务新的请求的&#xff1b;如果这台服务器…...

[项目总结] 在线OJ刷题系统项目技术应用(下)

&#x1f338;个人主页:https://blog.csdn.net/2301_80050796?spm1000.2115.3001.5343 &#x1f3f5;️热门专栏: &#x1f9ca; Java基本语法(97平均质量分)https://blog.csdn.net/2301_80050796/category_12615970.html?spm1001.2014.3001.5482 &#x1f355; Collection与…...

链表算法中常用操作和技巧

目 1.常用技巧 1.1.画图 1.2.添加虚拟头节点 1.3.大胆引入中间变量 1.4.快慢双指针 1.4.1判断链表是否有环 1.4.2找链表中环的入口 ​2.常用操作 2.1. 创建一个新节点 2.2.尾插 2.3.头插 1.常用技巧 1.1.画图 画图可以让一些抽象的文字语言更加形象生动 画图&#…...

MySQL基础 [二] - 数据库基础

目录 库的增删查改 查看数据库 创建数据库 删除数据库 修改数据库 认识系统编码&#xff08;字符集和校验规则&#xff09; 查看系统默认字符集以及校验规则 查看数据库支持的字符集和字符集校验规则 验证不同校验码编码的影响 校验规则对数据库的影响 数据库的备份…...

【Linux篇】基础IO - 文件描述符的引入

&#x1f4cc; 个人主页&#xff1a; 孙同学_ &#x1f527; 文章专栏&#xff1a;Liunx &#x1f4a1; 关注我&#xff0c;分享经验&#xff0c;助你少走弯路&#xff01; 文章目录 一. 理解文件1.1 侠义理解1.2 广义理解1.3 文件操作的归类认知1.4 系统角度 二. 回顾C语言文件…...

13.【.NET 8 实战--孢子记账--从单体到微服务--转向微服务】--微服务基础工具与技术--Refit

在微服务架构中&#xff0c;不同服务之间经常需要相互调用以完成复杂业务流程&#xff0c;而 Refit 能让这种“跨服务调用”变得简洁又可靠。开发者只需将对外暴露的 REST 接口抽象成 C# 接口&#xff0c;并通过共享库或内部 NuGet 包在各服务中引用&#xff0c;这种契约优先的…...

C++ 并发性能优化实战:提升多线程应用的效率与稳定性

&#x1f9d1; 博主简介&#xff1a;CSDN博客专家、CSDN平台优质创作者&#xff0c;获得2024年博客之星荣誉证书&#xff0c;高级开发工程师&#xff0c;数学专业&#xff0c;拥有高级工程师证书&#xff1b;擅长C/C、C#等开发语言&#xff0c;熟悉Java常用开发技术&#xff0c…...

前端性能优化的全方位方案【待进一步结合项目】

以下是前端性能优化的全方位方案&#xff0c;结合代码配置和最佳实践&#xff0c;涵盖从代码编写到部署的全流程优化&#xff1a; 一、代码层面优化 1. HTML结构优化 <!-- 语义化标签减少嵌套 --> <header><nav>...</nav> </header> <main&…...

(undone) 并行计算 CS149 Lecture3 (现代多核处理器2 + ISPC编程抽象)

url: https://www.bilibili.com/video/BV1du17YfE5G?spm_id_from333.788.videopod.sections&vd_source7a1a0bc74158c6993c7355c5490fc600&p3 如上堂课&#xff0c;超线程技术通过储存不同线程的 execution context&#xff0c;能够在一个线程等待 IO 的时候低成本切换…...

DiffAD:自动驾驶的统一扩散建模方法

25年3月来自新加坡公司 Carion 和北航的论文“DiffAD: A Unified Diffusion Modeling Approach for Autonomous Driving”。 端到端自动驾驶 (E2E-AD) 已迅速成为实现完全自动驾驶的一种有前途的方法。然而&#xff0c;现有的 E2E-AD 系统通常采用传统的多任务框架&#xff0c…...

QScrollArea 内部滚动条 QSS 样式失效问题及解决方案

在使用 Qt 进行 UI 开发时,我们经常希望通过 QSS(Qt Style Sheets)自定义控件的外观,比如为 QScrollArea 的内部滚动条设置特定的样式。然而,有开发者遇到了这样的问题:在 UI 设计器中预览 QSS 显示效果正常,但程序运行时却显示为系统默认样式。经过反复测试和调试,最终…...

换脸视频FaceFusion3.1.0-附整合包

2025版最强换脸软件FaceFusion来了&#xff08;附整合包&#xff09;超变态的AI换脸教程 2025版最强换脸软件FaceFusion来了&#xff08;附整合包&#xff09;超变态的AI换脸教程 整合包地址&#xff1a; 「Facefusion_V3.1.0」 链接&#xff1a;https://pan.quark.cn/s/f71601…...

Qt 入门 1 之第一个程序 Hello World

Qt 入门1之第一个程序 Hello World 直接上操作步骤从头开始认识&#xff0c;打开Qt Creator&#xff0c;创建一个新项目&#xff0c;并依次执行以下操作 在Qt Creator中&#xff0c;一个Kits 表示一个完整的构建环境&#xff0c;包括编译器、Qt版本、调试器等。在上图中可以直…...

无锁队列简介与实现示例

1. 简介 无锁队列是一种数据结构&#xff0c;旨在在多线程环境中实现高效的并发访问&#xff0c;而无需使用传统的锁机制&#xff08;如互斥锁&#xff09;。无锁队列通过使用原子操作&#xff08;如CAS&#xff0c;Compare-And-Swap&#xff09;来确保线程安全&#xff0c;从…...