簡體   English   中英

用const char *替換std :: string *

[英]replaceing std::string with const char*

我想知道有人可以幫我實現這個方法,而我不需要使用std :: string。

該方法接受tewo參數,一個用於char數組,另一個用於char數組的大小。

傳遞的參數將是一個由逗號分隔的不同值的數組,例如“ Rule1,Rule2,Rule3,Rule4,AT,T,Cat,Dog”。

成員變量“ m_rulesSet”是包含模擬值的std :: string。 我想比較兩者以檢查“名稱”是否在std :: string“ m_ruleSet”中

bool 
Matche(const char *str, size_t strSize)
{
    std::string target(str, strSize);

    if(m_ruleSet.empty())
    {
        return true;
    }
    if((NULL == str) || (strSize <= 0))
    {
        return false;
    }

    const char * ptr =0;
    const char * start = target.c_str();

    while ((ptr = strchr(start, ',')) != 0)
    {
        std::string name(start, ptr - start);
        if(name ==m_ruleSet)
        {
            return true;
        }
        start = ptr + 1;
    }
    if(*start)
    {
        std::string name(start);
        if(name==m_ruleSet)
        {
            return true;
        }
    }
    return false;
}

請任何幫助將不勝感激,非常感謝您

看起來您只是在使用std::string持有一個子字符串,然后進行比較。 為了進行子字符串比較而進行復制是無效的。

代替

std::string name(start, ptr - start);
if(name ==m_ruleSet)

你可以寫

if (ptr - start == m_ruleSet.size() && 0 == strncmp(start, m_ruleSet.c_str(), ptr-start))

您還應該使用memchr並傳入strstrSize ,而不是將target strSize std::string

我的總體建議是使用適當的詞法識別器/語法識別器,例如flex + bison。 這將比單獨調用strchrstrncmp更快地生成優化的DFA。 如果您有多個字符串(規則)要匹配,這特別有價值。


但是這是一個簡單的DFA:

bool csv_match( const char * const haystack, size_t const haystack_size, const char* const needle, size_t const needle_size )
{
    const char * const haystack_end = haystack + haystack_size;
    int state = 0;
    // invariant: state == -1 if the current field doesn't match
    //            otherwise the first (state) characters have been matched
    for( const char* p = haystack; p < haystack_end; ++p ) {
        if (*p == ',') {
            if (state == needle_size) return true;
            state = 0;
        }
        else if (state < 0)
            ;
        else if (state >= needle_size || *p != needle[state])
            state = -1;
        else
            ++state;
    }
    return (state == needle_size);
}

像這樣使用

bool Matche(const char *str, size_t strSize) const { return csv_match(std, strSize, m_ruleSet.data(), m_ruleSet.size()); }

因此,您只是strncmp strcmpstrncmp代替std::string比較(因為這是您唯一使用std::string的東西,其他所有東西都已經在使用C字符串了)? 好吧,如果您真的想要它:

bool Matche(const char *str, size_t strSize)
{
    if(m_ruleSet.empty())
        return true;
    if(!str || !strSize)     //remember that size_t is unsigned by standard
        return false;

    const char * ptr, start = str;
    while (ptr = memchr(start, ',', strSize))
    {
        size_t len = ptr - start;
        if(len == m_ruleSet.size() && !strncmp(start, m_ruleSet.c_str(), len))
            return true;
        strSize -= len + 1;
        start = ptr + 1;
    }
    return *start ? (strSize == m_ruleSet.size() && 
                     !strncmp(start, m_ruleSet.c_str(), strSize)) : false;
}

就像Ben在他的評論和答案中指出的那樣,當您獲得額外的size參數並且字符串不必以零strchr時,需要使用memchr而不是strchr

您可能m_ruleSet用C字符串替換m_ruleSet (以擺脫.c_str() ),但實際上我首先質疑在C ++代碼中用C字符串替換std::string的需要。

string.h / cstring提供了大多數用於字符串/基本內存操作的方法。 您應該能夠找到其中幾乎所有std::string方法的替代品。 當您找不到直接映射時,可以使用cstring方法自己編寫一個。 查看您發布的代碼,肯定需要strcpystrncpy (或memcpy )。

如果您有特定問題,請將其添加到帖子中,然后有人會幫助您。

所以您從std :: string使用的方法是

  • 字符* ctor

std::string target(str, strSize); => char * target = strdup(str)或strcpy

  • .empty()

m_ruleSet.empty() => strlen(m_ruleSet.c_str())==0

  • 比較方式

name==m_ruleSet => strcmp(name.c_str(),m_ruleSet.c_str()) == 0

你的意思是像重寫

std::string name(start);
if(name==m_ruleSet)
{
    return true;
}
return false;

進入

return m_ruleSet == start;

無需構造std::string即可將其與C字符串進行比較。 std::string的==運算符仍然可以正常工作。

如果您需要將m_ruleSet與另一個std::string或C字符串的子std::string::compare ,則std::string::compare一些重載就可以做到這一點。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM