Windows下C++解析程序的启动参数

为了方便控制程序的各种功能的开关和特性

我们往往会在程序启动的时候加入各种参数来控制程序的某些特性,或是传入一些数据。

本例提供了比较方便的代码段来供处理这些事宜。

代码段是[CmdlineParser]类的具体实现

CmdlineParser.hpp

#pragma once

#include <string>
//#include <tchar.h>
#include <stdint.h>
#include <map>
#include <algorithm>

/***********************************************************************
        参数间以空格分隔,如果参数本身含有空格,则需要用双引号包围
***********************************************************************/

class Param
{
public:
    Param(const std::string& value)
        : m_value(value)
    {
    }

    ~Param()
    {
    }

    std::string toString()
    {
        return m_value;
    }

    int32_t toInt()
    {
        return atoi(m_value.c_str());
    }

    int64_t toInt64()
    {
        return _atoi64(m_value.c_str());
    }

    uint32_t toUInt()
    {
        char* end_ptr = nullptr;
        return strtoul(m_value.c_str(), &end_ptr, 0);
    }

    uint64_t toUInt64()
    {
        char* end_ptr = nullptr;
        return _strtoui64(m_value.c_str(), &end_ptr, 0);
    }

private:
    std::string m_value;
};

class CmdlineParser
{
public:
    CmdlineParser(const std::string& cmdline)
    {
        analyze(cmdline);
    }

    ~CmdlineParser()
    {
    }

    std::string getFullCmdLine()
    {
        return m_strCmdLine;
    }

    bool analyze(const std::string& cmdline)
    {
        bool bResult = false;
        int nPos = 0, nParamNamePos = 0, nParamValuePos = 0;
        int nStatus = 0;

        std::string strParamName;
        bool bInComma = false;
        char chPos = '\0';

        if (cmdline.empty())
            goto Exit0;

        m_strCmdLine = cmdline;

        for (int nPos = 0; 0 == nPos || '\0' != cmdline[nPos - 1]; nPos ++)
        {
            chPos = cmdline[nPos];

            switch (nStatus)
            {
            case 0:

                if (bInComma)
                {
                    if ('\"' == chPos)
                        bInComma = false;
                }
                else if ('-' == chPos || '/' == chPos)
                    nStatus = 1;
                else if ('\"' == chPos)
                    bInComma = true;

                break;

            case 1:
                nParamNamePos = nPos;

                nStatus = 2;
                break;

            case 2:
                if (' ' == chPos || '\0' == chPos)
                {
                    strParamName = m_strCmdLine.substr(nParamNamePos, nPos - nParamNamePos);
                    setParam(strParamName, (uint32_t)1);

                    nStatus = 0;
                }
                else if ('=' == chPos)
                {
                    strParamName = m_strCmdLine.substr(nParamNamePos, nPos - nParamNamePos);
                    nStatus = 3;
                }

                break;

            case 3:
                if ('\"' == chPos)
                {
                    nPos ++;
                    bInComma = true;
                }
                else if (' ' == chPos || '\0' == chPos)
                {
                    setParam(strParamName, "");
                    nStatus = 0;

                    break;
                }

                nParamValuePos = nPos;
                nStatus = 4;

                break;

            case 4:
                if ((' ' == chPos && !bInComma) || '\0' == chPos || ('\"' == chPos && bInComma))
                {
                    setParam(strParamName, m_strCmdLine.substr(nParamValuePos, nPos - nParamValuePos));
                    nStatus = 0;
                    bInComma = false;
                }

                break;
            }
        }

        bResult = true;

    Exit0:

        return bResult;
    }

    bool hasParam(const std::string& param_name)
    {
        std::string param = param_name;
        std::transform(param.begin(), param.end(), param.begin(), tolower);

        CmdParamMap::iterator iter = m_mapParams.find(param);
        if(iter != m_mapParams.end())
        {
            return true;
        }

        return false;
    }

    bool setParam(const std::string& param_name, const std::string& param_value)
    {
        std::string param = param_name;
        std::transform(param.begin(), param.end(), param.begin(), tolower);
        m_mapParams[param] = param_value;

        return true;
    }

    bool setParam(const std::string& param_name, uint32_t param_value)
    {
        std::string param = param_name;
        std::transform(param.begin(), param.end(), param.begin(), tolower);

        char value[128] = { 0 };
        sprintf_s(value, "%d", param_value);

        m_mapParams[param] = value;

        return true;
    }

    bool setParam(const std::string& param_name, uint64_t param_value)
    {
        std::string param = param_name;
        std::transform(param.begin(), param.end(), param.begin(), tolower);

        char value[128] = { 0 };
        sprintf_s(value, "%I64d", param_value);

        m_mapParams[param] = value;

        return true;
    }

    Param operator[](const std::string& param_name)
    {
        std::string param = param_name;
        std::transform(param.begin(), param.end(), param.begin(), tolower);

        std::string value = "";

        CmdParamMap::iterator iter = m_mapParams.find(param);
        if(iter != m_mapParams.end())
        {
            value = iter->second;
        }

        return Param(value);
    }


protected:
    typedef std::map<std::string, std::string> CmdParamMap;

    std::string m_strCmdLine;
    CmdParamMap m_mapParams;
};

使用方式:


LPSTR lpcmdline = GetCommandLineA();
std::string strCmdLine = (lpcmdline == nullptr ? "" : lpcmdline);
CmdlineParser cmdLine(strCmdLine);
	
if( cmdLine.hasParam("wnd"))
{
	HWND hwndEmbed = (HWND)cmdLine["wnd"].toUInt();
	if( IsWindow(hwndEmbed))
		m_cmdLineData.hwndEmbed = hwndEmbed;
}	

if(cmdLine.hasParam("notifywnd"))
{
	HWND hnotifywnd = (HWND)cmdLine["notifywnd"].toUInt();
	if( IsWindow(hnotifywnd))
		m_cmdLineData.hNotifywnd = hnotifywnd;
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值