C++:使用 LSD 基数排序对字符串进行排序崩溃
Posted
技术标签:
【中文标题】C++:使用 LSD 基数排序对字符串进行排序崩溃【英文标题】:C++: Sorting strings using LSD radix sort crashing 【发布时间】:2015-04-30 21:28:51 【问题描述】:我编写了一些代码,旨在使用基数排序对字符串数组进行排序,从最低有效数字开始。此函数假定所有字符串的长度相同,并且每个字符都是小写的。
每当我进入将值分配给临时数组的循环时,我都会遇到崩溃。你可以在这里看到我的功能:
#ifndef RADIX_H
#define RADIX_H
#include <string>
#include <iostream>
using namespace std;
void lsd_string_radix(string array[], int array_size, int max_chars)
string *temp = new string[array_size];
for(int i = max_chars - 1; i >= 0; i--)
int count[26] = 0;
for(int j = 0; j < array_size; j++)
count[static_cast<int>(array[j][i]) - 97]++;
for(int j = 1; j <= 26; j++)
count[j] += count[j - 1];
for(int j = 0; j < array_size; j++)
temp[count[static_cast<int>(array[j][i])]++] = array[j]; // crashes here
for(int j = 0; j < array_size; j++)
array[j] = temp[j];
#endif
我猜我的逻辑有问题,但我一辈子都想不通。
【问题讨论】:
您是否只是在它崩溃的行中缺少-97
?
string array[]
作为const &std::vector<std::string>
参考值传入的值可能会好很多。积极使用static_cast
进行排序也可能适得其反。为什么不转换和排序?标准容器使这很容易实现。
【参考方案1】:
在第二个循环之后,count[0] 应该为零,而第三个循环缺少 -97。此示例使用大小为 27 而不是 26 的计数解决了问题。此示例中的第一个循环使用 -96,因此 count[0] = 0, count[1] = # instances of 'a's, count[2] = # instances的'b's,...... count[26] = # 'z's 的实例,但它只在第一个循环中使用。这不是必需的,但是将 'z' 的计数放在那里而不是添加 if 语句以避免将计数存储在 count[26] 处更简单。
#include<iomanip>
#include<iostream>
#include <string>
using namespace std;
void lsd_string_radix(string array[], int array_size, int max_chars)
string *temp = new string[array_size];
for(int i = max_chars - 1; i >= 0; i--)
int count[27] = 0;
for(int j = 0; j < array_size; j++)
count[static_cast<int>(array[j][i]) - 96]++;
for(int j = 2; j < 26; j++)
count[j] += count[j - 1];
for(int j = 0; j < array_size; j++)
temp[count[static_cast<int>(array[j][i]) - 97]++] = array[j];
for(int j = 0; j < array_size; j++)
array[j] = temp[j];
int main()
string a[6] = "mnop", "ijkl", "efgh", "uvwx", "qrst", "abcd";
lsd_string_radix(a, 6, 4);
for(size_t i = 0; i < 6; i++)
cout << a[i] << endl;
return 0;
如果count[]的大小为26,则需要修改第一个循环:
for(int j = 0; j < array_size; j++)
if(array[j][i] == 'z')continue;
count[static_cast<int>(array[j][i]) - 96]++;
或者修改前两个循环:
for(int j = 0; j < array_size; j++)
count[static_cast<int>(array[j][i]) - 97]++;
int m = 0;
int n;
for(int j = 0; j < 26; j++)
n = count[j];
count[j] = m;
m += n;
【讨论】:
效果很好,非常感谢。你介意解释为什么count[27]
更有意义吗?我仍然不太清楚这个概念。以上是关于C++:使用 LSD 基数排序对字符串进行排序崩溃的主要内容,如果未能解决你的问题,请参考以下文章