繁体   English   中英

以大写第一字母顺序C ++排列字符串

[英]Arranging a string in uppercase-first alphabetical order C++

我试图用C ++创建一个程序,按照字母顺序对给定字符串进行排序,其方式是大写字母在它们的小写等价物之前。 示例:DCBAdcba已排序字符串:AaBbCcDd

以下是代码。

#include <iostream>
#include <string>
#include <cctype>
struct char_ {
    char c;
    char diff;
    char_();
    char_(char x);
};
char_::char_() {
    c = 0;
    diff = 0;
}
char_::char_(char x) {
    c = std::tolower(x);
    diff = c - x;
}

void charswap(char_& x, char_& y) {
    char_ temp;
    temp = x;
    x = y;
    y = temp;
}

int main() {
    std::string str;
    getline(std::cin, str);
    char_* str2 = new char_[str.length()];
    for (int i = 0; i < str.length(); i++) {
        str2[i] = char_(str[i]);
    }

    /*
    for (int i = 0; i < str.length(); i++) {
        std::cout << str2[i].c << std::endl;
    }
    */
    for (int i = 0; i < str.length(); i++) {
        for (int j = i; j < str.length(); j++) {
            if (str2[i].c > str2[j].c)
                charswap(str2[i], str2[j]);
        }
    }


    for (int k = 0; k < str.length(); k++) {
    std::cout << str2[k].c << "\t" << (int)str2[k].diff << std::endl;
    }

    for (int i = 0; i < str.length(); i++) {

    str2[i].c = str2[i].c - str2[i].diff;
    }




    for (int i = 0; i < str.length(); i++) std::cout << str2[i].c;
    std::cout << "\n";
    return 0;
}

创建char_ struct以存储单个字符(转换为小写)以及它们与大写等效项的区别(0或32,具体取决于原始字符分别是小写字母还是大写字母)。 然后它根据它们的小写值对char_字符进行排序。 在排序之后,我们将差异添加回字符以检索大写形式。

但是当我尝试给出这个字符串时,它给出了以下结果。

DCBAdcba

AABBCCDD

我无法理解这里发生了什么。

问题出在这一行:

if (str2[i].c > str2[j].c)
    charswap(str2[i], str2[j]);

它以不区分大小写的方式比较字符,当小写字符相同时没有提供打破平局的规定。

如果右侧的小写大于左侧的小写,或者小写表示相同,但​​右侧原始字符为大写,则需要修改此项以交换字符:

if ((str2[i].c > str2[j].c) || (str2[i].c == str2[j].c && str2[j].diff))
    charswap(str2[i], str2[j]);

按字母顺序对给定字符串进行排序,其方式是大写字母位于其小写等效字母之前。

您可以定义一个反映您意图的比较仿函数

#include <cctype>
#include <iostream>
#include <vector>
#include <algorithm>

struct case_cmp {
    bool operator()(char lhs, char rhs) const {
        return (std::isupper(lhs) && std::tolower(lhs) == rhs) || std::tolower(lhs) < std::tolower(rhs);
    }
};

然后使用std::sort

int main() {
    std::string s("DCBAdcba");
    std::sort(std::begin(s), std::end(s), case_cmp());
    // Outputs "AaBbCcDd"
    std::cout << s << std::endl;
}

std::string可以被视为char容器 ,因此你可以将STL的算法应用于其内容,包括std::sort() (就像你将STL算法应用于例如std::vector )。

您可以使用lambda指定特定的自定义排序条件 ,作为第三个参数传递给std::sort() ,例如( 在Ideone上生效 ):

#include <algorithm>    // for std::sort
#include <cctype>       // for std::isupper, std::tolower
#include <iostream>     // for std::cout
#include <string>       // for std::string
using namespace std;

int main() {
    string s{"DCBAdcba"};

    sort( s.begin(), s.end(), [](char x, char y) { 
        // Custom sorting criteria.
        // Return true if x precedes y.

        // This may work, but requires more testing...
        if (isupper(x)) {
            if (tolower(x) == y) {
                return true;    
            }   
        }
        return tolower(x) < tolower(y);
    });

    cout << s << '\n';
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM