Visual Studio 2017 批量去掉代码优化的方法


  • 网站研运

    由于我们在二次开发的过程中,需要采用调试来测试开发的效果,而使用cmake生成的Visual Studio项目,代码都是O2优化的,不太符合我们的需求,而我们必须每次都要载入Visual Studio 2017手动修改代码优化到禁用,这的确有一些麻烦,于是我们需要找一个更加便利的方法达到效果。我在稍微研究了一下之后得到结论:其实很好解决。

    准备环境

    Windows 10
    Visual Studio 2017
    Notepad++

    随便打开一个vcxproj文件,然后按下快捷键:Ctrl + F,转到文件查找一栏。按照下面的要求填写:

    文件类型 *.vcxproj
    查找目标 <Optimization>MaxSpeed</Optimization>
    替换为 <Optimization>Disabled</Optimization>

    然后点击“在文件中替换”,等待一会儿,就可以看到优化全部去掉了。这样就可以顺利地单步调试而不会出现断点下不了或者是其它问题了。
    替换代码优化



  • 脚本玩家路过一下😁
    我写了一段Powershell脚本,可以一键打开/关闭调试信息和代码优化。
    原理就是解析.sln文件(xml格式),找到关联的所有.vcproj文件(也是xml格式),并把其中的字段修改掉。

    看脚本

    # filename: DebugInfoSwitch.ps1
    Add-Type -AssemblyName System.Xml.Linq
    
    # 获取绝对路径
    function GetAbsolutePath {
        [OutputType([string])]
        param([string]$filePath)
    
        $aPath = Resolve-Path $filePath
    
        return Split-Path $aPath
    }
    # 解析sln文件,提取出project列表
    function ParseSolution {
        [OutputType([string[]])]
        param([string]$solutionFile)
    
        $parttern = [regex]"^Project*"
        [string[]] $projs = @()
        Get-Content $solutionFile | Where-Object {$_ -match $parttern} | ForEach-Object {
            $items = $_.ToString().Split(',')
            
            if ($items[1].EndsWith("vcxproj`"")) {
                $projs += $items[1]
            }
        }
        return $projs
    }
    #Write-Host($debugGroup | Format-Table | Out-String )
    function UpdateDebugInfo {
        param([System.Xml.Linq.XNamespace]$xNamespace,[System.Xml.Linq.XElement] $group, [bool]$isOpen)
        [System.Xml.Linq.XElement]$xClCompile =  $group.Element($xNamespace + "ClCompile")
        [System.Xml.Linq.XElement]$xLink =  $group.Element($xNamespace + "Link")
        [System.Xml.Linq.XElement]$format = $xClCompile.Element($xNamespace + "DebugInformationFormat")
        [System.Xml.Linq.XElement]$optimization = $xClCompile.Element($xNamespace + "Optimization")
        [System.Xml.Linq.XElement]$generate = $xLink.Element($xNamespace + "GenerateDebugInformation")
        if ($null -eq $format) {
            $format = [System.Xml.Linq.XElement]::new($xNamespace + "DebugInformationFormat")
            $xClCompile.Add($format)
        }
        if ($null -eq $optimization) {
            $optimization = [System.Xml.Linq.XElement]::new($xNamespace + "Optimization")
            $xClCompile.Add($optimization)
        }
        if ($null -eq $generate) {
            $generate = [System.Xml.Linq.XElement]::new($xNamespace + "GenerateDebugInformation")
            $xLink.Add($generate)
        }
        if ($isOpen) {
            $format.SetValue("ProgramDatabase");
            $optimization.SetValue("Disabled");
            $generate.SetValue("true");
        } else {
            $format.SetValue("None");
            $optimization.SetValue("MaxSpeed");
            $generate.SetValue("false");
        }
    }
    function SwitchDebugInfo {
        param([string]$projPath, [bool]$open, [bool]$isRelease)
        if (Test-Path($projPath)) {
            [System.Xml.Linq.XDocument]$xDoc = [System.Xml.Linq.XDocument]::Load($projPath)
            [System.Xml.Linq.XNamespace]$xNamespace = $xDoc.Root.GetDefaultNamespace();
            [System.Xml.Linq.XElement]$group = $null
            $groups = $xDoc.Root.Elements($xNamespace + "ItemDefinitionGroup")
            foreach ($i in $groups) {
                if ($isRelease) {
                    if ($i.Attribute("Condition").Value -match "^*Release*") 
                    {
                        $group = $i;
                        break;
                    }
                } else {
                    if ($i.Attribute("Condition").Value -match "^*Debug*") 
                    {
                        $group = $i;
                        break;
                    }
                }
            }
            UpdateDebugInfo $xNamespace $group $open
            $xDoc.Save($projPath)
         }
    }
    #脚本入口函数
    function Main {
        param([string]$sln, [bool]$open, [bool]$isRelease)
        Write-Host("sln file ", $sln)
        $slnPath= GetAbsolutePath $sln
        $projList = ParseSolution $sln 
        $t = $projList.Split(' ') | ForEach-Object {
            $s = $_.ToString()
            if ($s) {
                $projPath=-Join($slnPath, '\', ($s.SubString(1, $s.Length - 2) ))
                SwitchDebugInfo $projPath $open $isRelease
            }
        }
    }
    function Usage {
        Write-Host ("Usage: DebugInfoSwitch.ps1 slnFilePath mode[D/d for Debug, R/r for Release] open[Y/y for open, N/n for close]")
        Write-Host ("Example for open Release mode debugInfo: DebugInfoSwitch.ps1 xxx.sln R y")
        Write-Host ("Example for close Debug mode debugInfo: DebugInfoSwitch.ps1 xxx.sln d N")
    }
    #检查参数
    [string]$sln = ""
    [bool]$open = $true
    [bool]$isRelease = $false
    if ( $args.Count -ne 3) {
        Usage
        return 
    }
    $sln = $args[0]
    if ($args[1] -eq "D" -or $args[1] -eq "d") {
        $isRelease = $false
    } elseif ($args[1] -eq "R" -or $args[1] -eq "r") {
        $isRelease = $true
    } else {
        Usage
        return
    }
    if ($args[2] -eq "Y" -or $args[2] -eq "y") {
        $open = $true
    } elseif ($args[2] -eq "N" -or $args[2] -eq "n") {
        $open = $false
    } else {
        Usage
        return
    }
    #调用主函数
    Main $sln $open $isRelease
    

    用的时候,再写个bat脚本,调用这个ps1并传参数就行了。
    比如打开Release模式的调试信息、同时关掉优化开关

    @echo off
    powershell.exe -NoProfile -ExecutionPolicy Bypass -File DebugInfoSwitch.ps1 ./you/path/to.sln R N
    

    关闭调试信息、打开优化开关,则是传相反的参数

    @echo off
    powershell.exe -NoProfile -ExecutionPolicy Bypass -File DebugInfoSwitch.ps1 ./you/path/to.sln R Y
    


  • @wentaojia2014
    代码中的 {1} 是自动生成的,注意删掉


  • 网站研运

    看了你的脚本,看来PowerShell是一种shell的方言,支持function和自定义的符号。和bash还不一样。
    我以前也写过Apple Script,看来大家都在shell语言上加上自己的特性啊。
    顺便了解到你们主要用Visual Studio开发Qt应用的。😁 😁


Log in to reply
 

走马观花

最近的回复

  • 诶 没有Linux吗??

    read more
  • 萌梦 男孩,女孩,和蛋

    menghome.png

    read more
  • 设计模式-工厂模式

    使用qt/qml来演示设计模式效果,便于学习理解

    1)定义创建对象的接口,封装对象的创建
    2)使具体化类的工作延迟到工厂子类中

    bg.png
    image.png

    1. 工厂类

    createProduct使用了参数来选择要创建哪个产品

    #ifndef FACTORY_H #define FACTORY_H #include <QObject> class Product; class QString; class Factory: public QObject { Q_OBJECT public: virtual ~Factory() = 0; virtual Product* createProduct(QString type) = 0; protected: Factory(); }; class ConcreteFactory: public Factory { Q_OBJECT public: ~ConcreteFactory(); ConcreteFactory(); public slots: Product* createProduct(QString type); }; #endif // FACTORY_H #include "factory.h" #include "product.h" #include <QtQml/qqml.h> Factory::~Factory() { } Factory::Factory() { qmlRegisterType<Product>("Product", 1, 0, "Product"); } ConcreteFactory::~ConcreteFactory() { } ConcreteFactory::ConcreteFactory() { } Product *ConcreteFactory::createProduct(QString type) { if(type == "boy") return static_cast<Product *>(new ConcreteProduct1()); else if(type == "girl") return static_cast<Product *>(new ConcreteProduct2()); return static_cast<Product *>(new ConcreteProduct1()); } 2 产品类

    一个产品是萌梦男,一个产品是萌梦女

    #ifndef PRODUCT_H #define PRODUCT_H #include <QObject> class Product: public QObject { Q_OBJECT public: virtual ~Product() = 0; Q_PROPERTY(QString icon READ icon NOTIFY iconChanged) QString m_icon; QString icon() const { return m_icon; } signals: void iconChanged(QString icon); protected: Product(); signals: public slots: }; class ConcreteProduct1: public Product { Q_OBJECT public: ~ConcreteProduct1(); ConcreteProduct1(); }; class ConcreteProduct2: public Product { Q_OBJECT public: ~ConcreteProduct2(); ConcreteProduct2(); }; #endif // PRODUCT_H #include "product.h" Product::~Product() { } Product::Product() { } ConcreteProduct1::~ConcreteProduct1() { } ConcreteProduct1::ConcreteProduct1() { m_icon = "qrc:/images/boy.png"; } ConcreteProduct2::~ConcreteProduct2() { } ConcreteProduct2::ConcreteProduct2() { m_icon = "qrc:/images/girl.png"; } 3. main.qml

    使用timer,canvas,listview等实现一个自动化生产的动画效果

    源代码

    Fork me on Gitee

    read more
  • blender建模 章鱼
    捕获2.PNG 😵

    read more

关注我们

微博
QQ群