C++ 用单词和数字按字母顺序排列字符串

C++ 用单词和数字按字母顺序排列字符串,c++,string,algorithm,vector,C++,String,Algorithm,Vector,我正在尝试找出如何按字母顺序排列包含单词和数字的单个字符串。正如您在下面看到的,我尝试过使用isdigit,但有些数字是负数,因此我的代码总是错误的。此外,我的代码将字符串拆分为子字符串,这些子字符串分别按字母顺序排列,但我不知道如何分别按字母顺序排列所有单词,将它们放回向量中的点,然后分别按字母顺序排列所有数字,并将它们放回点。有人能帮忙吗 编辑: 样本输入#1: 样本输出#1: 样本输入#2: 样本输出#2: 到目前为止,我的代码如下所示: vector<string> numb

我正在尝试找出如何按字母顺序排列包含单词和数字的单个字符串。正如您在下面看到的,我尝试过使用
isdigit
,但有些数字是负数,因此我的代码总是错误的。此外,我的代码将字符串拆分为子字符串,这些子字符串分别按字母顺序排列,但我不知道如何分别按字母顺序排列所有单词,将它们放回向量中的点,然后分别按字母顺序排列所有数字,并将它们放回点。有人能帮忙吗

编辑:

样本输入#1:

样本输出#1:

样本输入#2:

样本输出#2:

到目前为止,我的代码如下所示:

vector<string> numbers; 
string str;
string x;                   
getline (cin, str);
stringstream ss(str);
while (ss >> x){
   numbers.push_back(x);
}

if (numbers.size()==1){
    cout << numbers[0] << endl;
    return 0;
}

vector<int> results(numbers.size());
for (int i=0;i<numbers.size();i++){
    char *a=new char[numbers[i].size()+1];
    a[numbers[i].size()]=0;
    memcpy(a,numbers[i].c_str(),numbers[i].size());
    if(isdigit(*a)==0)
    {
        results[i]=1;
    } else{
        results[i]=0;
    }
}

int j=0;
while (j<numbers.size()){
    int k=j+1;
    while (k<numbers.size()){
        while (results[j]==results[k]){
            sort(numbers.begin()+j,numbers.begin()+k+1);
            k++;
        }
        j=k;
        k=numbers.size();
    }
    if(j==numbers.size()){
        for (int i=0; i<numbers.size();i++){
            cout << numbers[i] << " ";
        }
        j++;
    }
}
向量数;
字符串str;
字符串x;
getline(cin,str);
stringstream ss(str);
while(ss>>x){
数字。推回(x);
}
if(numbers.size()==1){

cout首先,您需要一个函数来确定字符串是否为数字。为此,请使用
strtol

#include <stdlib.h> // strtol

bool is_number( const std::string &str, long &num )
{
    char *p;
    num = strtol( str.c_str(), &p, 10 );
    return *p == '\0';
}
使用
std::sort
,对
std::vector

// include <algorithm> // sort

std::vector< std::string > numbers;
.... 
std::sort( numbers.begin(), numbers.end(), sortFunc );
如果您想知道每个字符串或数字在原始
向量中的位置,请使用
std::map

#include <map>

std::vector< std::string > numbers;
....
std::map< std::string, size_t > mapStr; // map string to index of string in vector numbers
std::map< long, size_t > mapNum;        // map number to index of number in vector numbers
for ( size_t index = 0; index < numbers.size(); index ++ )
{
    long num;
    if ( is_number( numbers[index], num ) )
        mapNum.emplace( num, index );
    else
        mapStr.emplace( numbers[index], index );
}

for ( auto & pa : mapNum )
    std::cout << pa.first << " pos " << pa.second << std::endl;
for ( auto & pa : mapStr )
    std::cout << pa.first.c_str() << " pos " << pa.second << std::endl;
您也可以使用
std::tuple
作为
std::map
的键:

std::vector< std::string > numbers;
....
std::map< std::tuple< bool, long, std::string>, size_t > mapTupleN;
for ( size_t index = 0; index < numbers.size(); index ++ )
{
    long num;
    bool is_num = is_number( numbers[index], num );
    mapTupleN.emplace( std::make_tuple( !is_num, num, numbers[index] ), index );
}
for ( auto & pa : mapTupleN )
{
    if ( !std::get<0>(pa.first) )
        std::cout << std::get<1>(pa.first) << " is number at position " << pa.second << std::endl;
    else
        std::cout << std::get<2>(pa.first).c_str() << " is string at position " << pa.second << std::endl;
}
std::vector数字;
....
std::map,size\u t>mapTupleN;
对于(size_t index=0;indexstd::cout在中读取元素时,对元素进行排序可能更容易

std::string input;
std::getline(std::cin, input);
std::stringstream ss(input);
std::vector<std::string> sorted;

while (ss >> input)
{
    bool alpha = 0 < std::isalpha(input[0]); //if it is a word
    for (std::size_t i = 0, e = sorted.size(); i != e; ++i)
    {
        if ((!!std::isalpha(sorted[i][0]) == alpha) && (alpha ? (input < sorted[i]) : (std::stoi(input) < std::stoi(sorted[i])))) //if input is <
            std::swap(sorted[i], input); //exchange places
    }
    sorted.emplace_back(std::move(input)); //insert input at end
}
std::字符串输入;
std::getline(std::cin,输入);
std::stringstream ss(输入);
std::向量排序;
while(ss>>输入)
{
bool alpha=0
每次循环
时,它都会检查第一个字符是否为字母。如果是字母,则必须为单词,否则为数字。然后,对于之前扫描的每个元素,它会检查它们是否为相同类型(字母/字母,数字/数字)。如果它们都是单词,则只对它们进行比较。如果它们是数字,则使用
stoi
将它们转换为整数并比较结果。如果比较得出
input
小于元素,则将元素与
input
交换。在
for
循环结束时,
input
是gre该类型的最新元素,并插入到后面


案例在这个比较中很重要(
'a'!='a'
),但如果它不重要,那么添加一个修复就很容易了。

我的2p。

std::string alphabetize(const std::string& s)
{
    // string parts here
    std::vector<std::string> a;

    // integer parts here
    std::vector<int> n;

    // remember the order of the input types (true = integer, false = string)
    std::vector<bool> type_is_int_list;

    // wrap input in a stream for easy parsing
    std::istringstream iss(s);

    // somewhere to read each part into
    std::string item;

    // extract one space-separated part at a time
    while(iss >> item)
    {
        int i;
        if(std::istringstream(item) >> i) // is item an integer?
        {
            n.push_back(i);
            type_is_int_list.push_back(true);
        }
        else
        {
            a.push_back(item);
            type_is_int_list.push_back(false);
        }
    }

    // sort both string and integer vectors
    std::sort(a.begin(), a.end());
    std::sort(n.begin(), n.end());

    // a place to rebuild the output from the input
    std::ostringstream oss;

    // keep track of where we are in each vector
    auto a_iter = a.begin();
    auto n_iter = n.begin();

    // element separator
    std::string sep;

    // scan originally-ordered list of types to rebuild positions
    for(bool type_is_int: type_is_int_list)
    {
        if(type_is_int)
            oss << sep << *n_iter++; // add next sorted number to output
        else
            oss << sep << *a_iter++; // add next sorted string to output

        sep = " "; // after first item need space separator
    }

    return oss.str(); // return the reconstructed string
}
std::string字母顺序(const std::string&s)
{
//这里是弦乐部分
std::载体a;
//这里是整数部分
std::向量n;
//记住输入类型的顺序(true=integer,false=string)
std::向量类型是int列表;
//将输入封装在流中以便于解析
标准:istringstream iss;
//读每一部分的地方
std::字符串项;
//一次提取一个空格分隔的部分
while(iss>>项目)
{
int i;
if(std::istringstream(item)>>i)//item是整数吗?
{
n、 推回(i);
类型是内部列表。向后推(true);
}
其他的
{
a、 推回(项目);
类型是内部列表。向后推(false);
}
}
//对字符串和整数向量进行排序
排序(a.begin(),a.end());
排序(n.begin(),n.end());
//从输入重新生成输出的位置
std::ostringstream oss;
//跟踪我们在每个向量中的位置
自动a_iter=a.begin();
自动n_iter=n.begin();
//元素分离器
std::字符串sep;
//扫描原始排序的类型列表以重建位置
for(布尔类型为:类型为列表)
{
if(类型为int)
oss这个怎么样

#include "iostream"
#include "algorithm"
#include "string"
#include "vector"
#include "cctype"
#include "unordered_map"
using namespace std;

int main()
{
    vector <string> all, s;
    vector <int> n;
    unordered_map <int, bool> number;
    string x;
    getline(cin, x);
    int prev=0;
    for (int i=0; i<x.length(); i++)
    {
        if (x[i]==' ')
        {
            all.push_back(x.substr(prev, i-prev+1));
            prev=i+1;
        }
    }
    all.push_back(x.substr(prev));
    for (int i=0; i<all.size(); i++)
    {
        if (isdigit(all[i].c_str()[0]) || isdigit(all[i].c_str()[1]))
        {
            n.push_back(atoi(all[i].c_str()));
            number[i]=1;
        }
        else s.push_back(all[i]);
    }
    sort(s.begin(), s.end());
    sort(n.begin(), n.end());
    for (int i=0, j=0, k=0; i<all.size(); i++)
    {
        if (number[i]) cout << n[j++] << ' ';
        else cout << s[k++] << ' ';
    }
}
#包括“iostream”
#包括“算法”
#包括“字符串”
#包括“向量”
#包括“cctype”
#包括“无序地图”
使用名称空间std;
int main()
{
向量all,s;
向量n;
无序的地图编号;
字符串x;
getline(cin,x);
int prev=0;

对于(int i=0;i请发布示例输入、预期输出和观察到的输出。您可以共享示例输入输出吗?需要确定您正在尝试执行的操作。
char*a=new char[numbers[i].size()+1]
Why??只提供了一些示例输入和输出。@Jeremy为什么不直接使用
std::string
?完全不需要执行您正在执行的操作。此外,还引入了内存泄漏。
string a=numbers[i]
谢谢你的帮助!我看到的唯一一件事是,此代码不会将单词/数字分别放回属于单词和数字的位置。@Jeremy如果你想知道每个字符串或数字在原始向量中的位置,请使用
std::map
。请参阅我答案的最后一部分。对不起,那么命名的向量在哪里rted来自?@Jeremy我意识到我忽略了这一点,我在中编辑了变量声明。也许你需要重新加载页面。这样看起来更好,但请注意,如果你不能事先预测元素的数量,我会相应地修改代码。我无法预测元素的数量谢谢你的帮助。我觉得这段代码很有用最具可读性,最容易理解!
std::vector< std::string > numbers;
....
std::vector< std::string > vStr;
std::vector< long > vNum;
for ( std::string &str: numbers )
{
    long num;
    if ( is_number( str, num )
        vNum.push_back( num );
    else
        vStr.push_back( str);
}
std::sort( vNum.begin(), vNum.end() );
std::sort( vStr.begin(), vStr.end() );
#include <map>

std::vector< std::string > numbers;
....
std::map< std::string, size_t > mapStr; // map string to index of string in vector numbers
std::map< long, size_t > mapNum;        // map number to index of number in vector numbers
for ( size_t index = 0; index < numbers.size(); index ++ )
{
    long num;
    if ( is_number( numbers[index], num ) )
        mapNum.emplace( num, index );
    else
        mapStr.emplace( numbers[index], index );
}

for ( auto & pa : mapNum )
    std::cout << pa.first << " pos " << pa.second << std::endl;
for ( auto & pa : mapStr )
    std::cout << pa.first.c_str() << " pos " << pa.second << std::endl;
std::vector< std::string > numbers;
....
std::map< std::string, size_t, bool(*)(const std::string &a, const std::string &b) > mapN( sortFunc );
for ( size_t index = 0; index < numbers.size(); index ++ )
    mapN.emplace( numbers[index], index );

for ( auto & pa : mapN )
    std::cout << pa.first << " pos " << pa.second << std::endl;
std::vector< std::string > numbers;
....
std::map< std::tuple< bool, long, std::string>, size_t > mapTupleN;
for ( size_t index = 0; index < numbers.size(); index ++ )
{
    long num;
    bool is_num = is_number( numbers[index], num );
    mapTupleN.emplace( std::make_tuple( !is_num, num, numbers[index] ), index );
}
for ( auto & pa : mapTupleN )
{
    if ( !std::get<0>(pa.first) )
        std::cout << std::get<1>(pa.first) << " is number at position " << pa.second << std::endl;
    else
        std::cout << std::get<2>(pa.first).c_str() << " is string at position " << pa.second << std::endl;
}
std::string input;
std::getline(std::cin, input);
std::stringstream ss(input);
std::vector<std::string> sorted;

while (ss >> input)
{
    bool alpha = 0 < std::isalpha(input[0]); //if it is a word
    for (std::size_t i = 0, e = sorted.size(); i != e; ++i)
    {
        if ((!!std::isalpha(sorted[i][0]) == alpha) && (alpha ? (input < sorted[i]) : (std::stoi(input) < std::stoi(sorted[i])))) //if input is <
            std::swap(sorted[i], input); //exchange places
    }
    sorted.emplace_back(std::move(input)); //insert input at end
}
std::string alphabetize(const std::string& s)
{
    // string parts here
    std::vector<std::string> a;

    // integer parts here
    std::vector<int> n;

    // remember the order of the input types (true = integer, false = string)
    std::vector<bool> type_is_int_list;

    // wrap input in a stream for easy parsing
    std::istringstream iss(s);

    // somewhere to read each part into
    std::string item;

    // extract one space-separated part at a time
    while(iss >> item)
    {
        int i;
        if(std::istringstream(item) >> i) // is item an integer?
        {
            n.push_back(i);
            type_is_int_list.push_back(true);
        }
        else
        {
            a.push_back(item);
            type_is_int_list.push_back(false);
        }
    }

    // sort both string and integer vectors
    std::sort(a.begin(), a.end());
    std::sort(n.begin(), n.end());

    // a place to rebuild the output from the input
    std::ostringstream oss;

    // keep track of where we are in each vector
    auto a_iter = a.begin();
    auto n_iter = n.begin();

    // element separator
    std::string sep;

    // scan originally-ordered list of types to rebuild positions
    for(bool type_is_int: type_is_int_list)
    {
        if(type_is_int)
            oss << sep << *n_iter++; // add next sorted number to output
        else
            oss << sep << *a_iter++; // add next sorted string to output

        sep = " "; // after first item need space separator
    }

    return oss.str(); // return the reconstructed string
}
#include "iostream"
#include "algorithm"
#include "string"
#include "vector"
#include "cctype"
#include "unordered_map"
using namespace std;

int main()
{
    vector <string> all, s;
    vector <int> n;
    unordered_map <int, bool> number;
    string x;
    getline(cin, x);
    int prev=0;
    for (int i=0; i<x.length(); i++)
    {
        if (x[i]==' ')
        {
            all.push_back(x.substr(prev, i-prev+1));
            prev=i+1;
        }
    }
    all.push_back(x.substr(prev));
    for (int i=0; i<all.size(); i++)
    {
        if (isdigit(all[i].c_str()[0]) || isdigit(all[i].c_str()[1]))
        {
            n.push_back(atoi(all[i].c_str()));
            number[i]=1;
        }
        else s.push_back(all[i]);
    }
    sort(s.begin(), s.end());
    sort(n.begin(), n.end());
    for (int i=0, j=0, k=0; i<all.size(); i++)
    {
        if (number[i]) cout << n[j++] << ' ';
        else cout << s[k++] << ' ';
    }
}