VSCode+Qt+MSVC环境配置

VSCode+Qt+MSVC配置

VSCode功能强大,使用也很舒服,但总是遇到各种坑;我在配置VSCode+Qt+MSVC时,网上也找了一堆资料,总是零零散散,好在配置成功了,希望大家以后少走弯路。

一 安装

  1. Win10 SDK 版本:10.0.22621.0。
  2. 安装Qt。我安装的是qt5.15.2 + MSVC。
  3. 安装VS。我安装的是VS2019.
  4. 安装VSCode。官网下载安装。
  5. VSCode插件安装。在VScode中安装配置QT必要插件:C/C++、Qt Configure、Qt tools。
    在这里插入图片描述
    请添加图片描述
    请添加图片描述
  6. 调试器:CDB。

二 环境配置

QT环境变量配置

C:\Qt\5.15.2\msvc2019_64;C:\Qt\5.15.2\msvc2019_64\bin;C:\Qt\Tools\QtCreator\bin。将这三个路径添加至环境变量。
请添加图片描述

cl编译器环境配置

  1. 创建INCLUDE环境变量,添加路径:C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Tools\MSVC\14.29.30133\include;C:\Program Files (x86)\Windows Kits\10\Include\10.0.22621.0\shared;C:\Program Files (x86)\Windows Kits\10\Include\10.0.22621.0\ucrt;C:\Program Files (x86)\Windows Kits\10\Include\10.0.22621.0\um;C:\Program Files (x86)\Windows Kits\10\Include\10.0.22621.0\winrt;10.0.22621.0为win10SDK版本,根据自己版本选择。
    在这里插入图片描述
    在这里插入图片描述
    注意:INCLUDE和LIB中的winSDK版本要一致,比如我使用的是10.0.22621版本,INCLUDE和LIB都选择设置为INCLUDE和LIB的版本。

  2. 进入cl.exe所在的路径:C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Tools\MSVC\14.29.30133\bin\Hostx64\x64;该路径下有cl.exe则为正确的。将该路径添加至环境变量Path下。请添加图片描述
    在这里插入图片描述

rc配置

​ 进入:C:\Program Files (x86)\Windows Kits\10\bin\10.0.22621.0\x64,拷贝rc.exe、rcdll.dll。
在这里插入图片描述
进入:C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Tools\MSVC\14.29.30133\bin\Hostx64\x64,将拷贝的rc.exe、rcdll.dll复制到该目录下。
在这里插入图片描述

三 VSCode配置

Qt创建一个项目,取消影子构建。运行一下,确定Qt工作正常。

在这里插入图片描述
使用VSCode打开,我这是已经配置好的,如果是新创建的Qt工程,只有默认的pro、h、cpp、ui等文件。

在这里插入图片描述

C/C++插件配置

​ 快捷键:ctrl+shift+p打开运行命令,输入C++,选择第一个编辑配置(UI),创建默认配置。
在这里插入图片描述
进入C/C++插件配置界面:

在这里插入图片描述
配置名称:一般都是Win32,除非系统是x86。

编辑器路径:一般都会默认选中cl.exe,不会显示路径。建议手动选择,将cl.exe的绝对路径添加进去,因为可能存在多个版本cl.exe。

在这里插入图片描述
IntelliSense 模式:选择windows-msvc-x64
在这里插入图片描述
包含路径:添加:C:/Qt/5.15.2/msvc2019_64/include/** ;该路径为qt msvc的include路径。
在这里插入图片描述
C标准和C++标准根据情况选择,我使用的是C17/C++17。

在这里插入图片描述C/C++插件配置完成后,会在工程目录下.vscode文件夹下生成一个c_cpp_properties.json配置文件,该json文件记录了C/C++插件的配置信息。另外.vscode文件夹默认是隐藏,可自行在文件管理器中设置不隐藏。

在这里插入图片描述

{
    "configurations": [
        {
            "name": "Win32",
            "includePath": [
                "${workspaceFolder}/**",
                "C:/Qt/5.15.2/msvc2019_64/include/**"
            ],
            "defines": [
                "_DEBUG",
                "UNICODE",
                "_UNICODE"
            ],
            "windowsSdkVersion": "10.0.22621.0",
            "compilerPath": "C:/Program Files (x86)/Microsoft Visual Studio/2019/Community/VC/Tools/MSVC/14.29.30133/bin/Hostx64/x64/cl.exe",
            "cStandard": "c17",
            "cppStandard": "c++17",
            "intelliSenseMode": "windows-msvc-x64"
        }
    ],
    "version": 4
}

配置task.json

选择终端-运行任务-配置任务-使用模板创建task.json文件-Others;会在.vscode文件下生成一个task.json的配置文件。

在这里插入图片描述
task.json的配置要和Qt配置一致,可以对照Qt构建界面。

在这里插入图片描述
qmake.exe在构建pro文件时会输入四个参数: -spec, win32-msvc,“CONFIG+=debug”,“CONFIG+=qml_debug”。这四个参数对应json文件中的args。

配置jom.exe:command修改为C:/Qt/Tools/QtCreator/bin/jom/jom.exe,最好使用绝对路径,如果你足够了解vscode可以使用相对路径。
在这里插入图片描述

{
    // See https://go.microsoft.com/fwlink/?LinkId=733558
    // for the documentation about the tasks.json format
    "version": "2.0.0",
    "tasks": [
        {
            //在当前项目目录创建build文件夹
            "label": "mkdir", //任务名称
            "type": "shell", //任务类型,定义任务是被作为进程运行还是在 shell 中作为命令运行。
            "options": {
                "cwd": "${workspaceFolder}" //已执行程序或脚本的当前工作目录,设置当前项目文件夹
            },
            "command": "mkdir", //命令
            "args": [ //命令后面跟的参数
                "-Force",
                "build"
            ]
        },
        {
            "label": "qmake-debug",
            "type": "shell",
            "options": {
                "cwd": "${workspaceFolder}/build" //进入build目录
            },
            "command": "C:/Qt/5.15.2/msvc2019_64/bin/qmake.exe", //qmake命令,这里没用完整路径,是因为配置到环境变量了 C:/Qt/5.15.2/mingw81_64/bin/qmake.exe
            "args": [ //跟的参数是不是很熟悉,就是上面分析出来的Qt Creator执行流程
                "../${workspaceFolderBasename}.pro", //在build目录上一级哦
                "-spec",
                "win32-msvc",
                "\"CONFIG+=debug\"",
                "\"CONFIG+=qml_debug\""
            ],
            "dependsOn": [ //这是本条命令依赖的前置条件,就是上面创建build文件夹的task,直接执行本task会自动先调用依赖的task
                "mkdir" //其实可以手动执行一次,后面不用每次都执行创建目录的操作
            ]
        },
        {
            "label": "make-debug",
            "type": "shell",
            "options": {
                "cwd": "${workspaceFolder}/build"
            },
            "command": " C:/Qt/Tools/QtCreator/bin/jom/jom.exe", //MinGW这个也配置在环境变量了,不用写完整路径了 C:/Qt/Tools/mingw810_64/bin/mingw32-make.exe
            "args": [
                "-f",
                "Makefile.Debug"//-f 选择makefile,这是qmake编译出来的
               // "-j7" //这个参数都知道吧,编译用的线程数量
            ],
            "dependsOn": [
                "qmake-debug"
            ]
        },
        {
            "label": "run-debug",
            "type": "process", //运行就不能选择shell执行了,要选择process
            "options": {
                "cwd": "${workspaceFolder}/build/debug" //没在.pro配置DESTDIR,会生成到build目录下面对应目录
            },
            "command": "${workspaceFolderBasename}.exe", //执行的exe名字,一般当前项目文件夹的名称,自定义可以写其他的
            "dependsOn": [
                "make-debug"
            ]
        },
        {
            "label": "qmake-release",
            "type": "shell",
            "options": {
                "cwd": "${workspaceFolder}/build"
            },
            "command": "C:/Qt/5.15.2/msvc2019_64/bin/qmake.exe",
            "args": [ //注意release跟debug参数的差异
                "../${workspaceFolderBasename}.pro",
                "-spec",
                "win32-msvc",
                "\"CONFIG+=qtquickcompiler\""
            ],
            "dependsOn": [
                // "mkdir" //不用每次都创建吧
            ]
        },
        {
            "label": "make-release",
            "type": "shell",
            "options": {
                "cwd": "${workspaceFolder}/build"
            },
            "command": " C:/Qt/Tools/QtCreator/bin/jom/jom.exe",
            "args": [
                "-f",
                "Makefile.Release" //注意release跟debug参数的差异
               // "-j7"
            ],
            "dependsOn": [
                "qmake-release"
            ]
        },
        {
            "label": "run-release",
            "type": "process",
            "options": {
                "cwd": "${workspaceFolder}/build/release"
            },
            "command": "${workspaceFolderBasename}.exe",
            "dependsOn": [
                "make-release"
            ]
        },
        {
            "label": "clean",
            "type": "shell",
            "options": {
                "cwd": "${workspaceFolder}/build"
            },
            "command": " C:/Qt/Tools/QtCreator/bin/jom/jom.exe",
            "args": [
                "clean"
            ]
        }
    ]
}

构建运行

快捷键:ctrl+shift+p打开运行命令,输入run task,选择第一个 Run Task。
在这里插入图片描述
选择run-debug
在这里插入图片描述
选择 继续而不扫描任务输出(根据自己的需要选择)

在这里插入图片描述
运行成功后,终端输出无报错,窗体正常显示。

在这里插入图片描述

配置调试器

MSVC使用的是CDB调试器,MinGW使用的是GDB调试,注意区分。MSVC貌似也可以使用GDB,但没有研究,所不做阐述。以下只是用CDB调试器。

在VSCode左侧选择运行与调试,点击创建launch.json。点击launch.json右下边点击添加配置,选择C/C++配置 gdb启动;这边添加的是GDB调试器,我们要配置的是CDB,不过无所谓,我们要的是一个模板。

{
    // 使用 IntelliSense 了解相关属性。 
    // 悬停以查看现有属性的描述。
    // 欲了解更多信息,请访问: https://go.microsoft.com/fwlink/?linkid=830387
    "version": "0.2.0",
    "configurations": [


        {
            "name": "debug cdb",
            "type": "cppvsdbg",
            "request": "launch",
            "program": "${workspaceFolder}/build/debug/${workspaceFolderBasename}.exe",
            "args": [],
            "stopAtEntry": false,
            "cwd": "${workspaceFolder}",
            "environment": [],
            "externalConsole": false,
            // 以下注释掉是因为我有配置CDB的环境变量
            // "setupCommands": [
            //     {
            //         "description": "为 cdb 启用整齐打印",
            //         "text": "-enable-pretty-printing",
            //         "ignoreFailures": true
            //     }
            // ],
           // "miDebuggerPath": "C:/Program Files (x86)/Windows Kits/10/Debuggers/x64/cdb.exe"
        }
    ]
}

随便打个断点,点击运行。

在这里插入图片描述

四 配置错误导致的问题

错误1:[‘cl’ 不是内部或外部命令,也不是可运行的程序]

在完成第二步环境配置后,ctrl+shift+p运行程序,在终端界面如果出现’cl’ 不是内部或外部命令,也不是可运行的程序,则说明cl环境变量配置错误,程序引用不到cl的环境导致错误。

如果环境没问题,注意下cl的版本,是否是x86、arm等。

在这里插入图片描述

错误2:[iostream: 不包括路径集]

与错误1原因是一致的,属于cl环境问题,程序未引用到cl。

错误3:[无法运行“rc.exe”]

在完成第二步环境配置后,ctrl+shift+p运行程序,在终端界面出现无法运行“rc.exe”。这个问题是cl无法引用到rc,rc是win10 SDK中的文件,将其拷贝到使用的cl路径下即可,注意rc版本要和cl对应,注意x86、arm等版本。

如果环境没问题,注意下cl的版本,是否是x86、arm等。

AVL树的插入和删除操作都需要对树进行旋转操作来保持AVL树的平衡性。下面是C语言实现的AVL树插入和删除操作: AVL树插入操作: ```c // AVL树节点定义 struct AVLNode { int key; int height; struct AVLNode* left; struct AVLNode* right; }; // 计算节点高度 int height(struct AVLNode* node) { if (node == NULL) { return 0; } return node->height; } // 右旋操作 struct AVLNode* rotate_right(struct AVLNode* y) { struct AVLNode* x = y->left; struct AVLNode* t2 = x->right; // 执行旋转 x->right = y; y->left = t2; // 更新高度 y->height = max(height(y->left), height(y->right)) + 1; x->height = max(height(x->left), height(x->right)) + 1; return x; } // 左旋操作 struct AVLNode* rotate_left(struct AVLNode* x) { struct AVLNode* y = x->right; struct AVLNode* t2 = y->left; // 执行旋转 y->left = x; x->right = t2; // 更新高度 x->height = max(height(x->left), height(x->right)) + 1; y->height = max(height(y->left), height(y->right)) + 1; return y; } // 计算平衡因子 int balance_factor(struct AVLNode* node) { if (node == NULL) { return 0; } return height(node->left) - height(node->right); } // 插入节点 struct AVLNode* avl_insert(struct AVLNode* node, int key) { // 执行BST插入 if (node == NULL) { struct AVLNode* new_node = (struct AVLNode*)malloc(sizeof(struct AVLNode)); new_node->key = key; new_node->height = 1; new_node->left = NULL; new_node->right = NULL; return new_node; } if (key < node->key) { node->left = avl_insert(node->left, key); } else if (key > node->key) { node->right = avl_insert(node->right, key); } else { // key已经存在,不需要插入 return node; } // 更新高度 node->height = max(height(node->left), height(node->right)) + 1; // 计算平衡因子 int bf = balance_factor(node); // 如果平衡因子大于1,需要进行旋转操作 if (bf > 1) { if (key < node->left->key) { // 左左情况,执行右旋操作 return rotate_right(node); } else { // 左右情况,先对左子树进行左旋操作,再对根节点进行右旋操作 node->left = rotate_left(node->left); return rotate_right(node); } } else if (bf < -1) { if (key > node->right->key) { // 右右情况,执行左旋操作 return rotate_left(node); } else { // 右左情况,先对右子树进行右旋操作,再对根节点进行左旋操作 node->right = rotate_right(node->right); return rotate_left(node); } } return node; } ``` AVL树删除操作: ```c // 查找最小值节点 struct AVLNode* find_min(struct AVLNode* node) { if (node == NULL) { return NULL; } if (node->left == NULL) { return node; } return find_min(node->left); } // 删除节点 struct AVLNode* avl_delete(struct AVLNode* node, int key) { // 执行BST删除 if (node == NULL) { return NULL; } if (key < node->key) { node->left = avl_delete(node->left, key); } else if (key > node->key) { node->right = avl_delete(node->right, key); } else { if (node->left == NULL || node->right == NULL) { // 被删除节点只有一个子节点或者没有子节点 struct AVLNode* temp = node->left ? node->left : node->right; if (temp == NULL) { // 没有子节点,直接删除 temp = node; node = NULL; } else { // 有一个子节点,用子节点替换被删除节点 *node = *temp; } free(temp); } else { // 被删除节点有两个子节点,找到右子树的最小值节点替换被删除节点 struct AVLNode* temp = find_min(node->right); node->key = temp->key; node->right = avl_delete(node->right, temp->key); } } if (node == NULL) { return NULL; } // 更新高度 node->height = max(height(node->left), height(node->right)) + 1; // 计算平衡因子 int bf = balance_factor(node); // 如果平衡因子大于1,需要进行旋转操作 if (bf > 1) { if (balance_factor(node->left) >= 0) { // 左左情况,执行右旋操作 return rotate_right(node); } else { // 左右情况,先对左子树进行左旋操作,再对根节点进行右旋操作 node->left = rotate_left(node->left); return rotate_right(node); } } else if (bf < -1) { if (balance_factor(node->right) <= 0) { // 右右情况,执行左旋操作 return rotate_left(node); } else { // 右左情况,先对右子树进行右旋操作,再对根节点进行左旋操作 node->right = rotate_right(node->right); return rotate_left(node); } } return node; } ``` 以上是AVL树的插入和删除操作的C语言实现。需要注意的是,AVL树的插入和删除操作都需要对树进行旋转操作来保持平衡,因此这些操作的时间复杂度是O(log n)。
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值