排序规则:
无
无
输入:
Hello hello world
输出:
Hello world
输入:
i LOVE Cc I love CC Hello Hel Hellow
输出:
Cc Hel Hello Hellow i LOVE
这题有两部分逻辑,一个是排序,一个是去重。
我这里是先排序后去重,因为我想基于栈结构去重,即排序后,不区分大小写的两个字符串一定是紧挨着的,因此后入栈的字符串如果和栈顶字符串相同(不区分大小写),则不入栈。
排序规则其实就是字典序。但是需要注意的是,不区分大小写排序,因此我们不能直接使用 Array.prototype.sort
的原生字典序排序,而是需要自定义不区分大小写的字典序排序。
读取输入:
分割单词:
split(' ')
方法将字符串按空格分割成单词数组。自定义排序:
Array.prototype.sort
方法对单词数组进行排序。去重:
输出结果:
Array.prototype.join
方法将栈中的单词拼接成一个字符串并输出。Hello hello world
Hello world
解释:
['Hello', 'hello', 'world']
['Hello', 'world']
i LOVE Cc I love CC Hello Hel Hellow
Cc Hel Hello Hellow i LOVE
解释:
['Cc', 'CC', 'Hel', 'Hello', 'Hellow', 'i', 'I', 'LOVE', 'love']
['Cc', 'Hel', 'Hello', 'Hellow', 'i', 'LOVE']
通过上述步骤,我们可以高效地对单词进行排序和去重,确保结果符合要求。这种方法的时间复杂度主要由排序操作决定,为 O(n log n)
,其中 n
是单词的个数。
以下是 JavaScript代码 的详细中文注释和讲解:
/* JavaScript Node ACM模式 控制台输入获取 */
const readline = require("readline"); // 引入readline模块,用于读取控制台输入
const rl = readline.createInterface({
input: process.stdin, // 设置输入流为标准输入
output: process.stdout, // 设置输出流为标准输出
});
// 监听控制台的输入事件
rl.on("line", (line) => {
const arr = line.split(" "); // 将输入的字符串按空格分割成数组
console.log(sortStr(arr)); // 调用sortStr函数并输出结果
});
// 定义sortStr函数,用于对字符串数组进行排序和去重
function sortStr(arr) {
// 对数组进行排序
arr.sort((a, b) => {
a = a.toLowerCase(); // 将字符串a转换为小写
b = b.toLowerCase(); // 将字符串b转换为小写
// 比较两个字符串的大小
return a === b ? 0 : a > b ? 1 : -1;
});
const stack = [arr.shift()]; // 创建一个栈,并将排序后的第一个元素放入栈中
// 遍历数组,进行去重操作
for (let str of arr) {
const top = stack.at(-1).toLowerCase(); // 获取栈顶元素并转换为小写
const add = str.toLowerCase(); // 获取当前元素并转换为小写
if (top === add) continue; // 如果栈顶元素与当前元素相同,跳过
stack.push(str); // 否则将当前元素压入栈中
}
return stack.join(" "); // 将栈中的元素用空格连接成字符串并返回
}
引入模块:
const readline = require("readline");
:引入readline
模块,用于读取控制台输入。创建接口:
const rl = readline.createInterface({ input: process.stdin, output: process.stdout });
:创建一个readline
接口,设置输入流为标准输入,输出流为标准输出。监听输入事件:
rl.on("line", (line) => { ... });
:监听控制台的输入事件,当用户输入一行内容时触发回调函数。const arr = line.split(" ");
:将输入的字符串按空格分割成数组。console.log(sortStr(arr));
:调用sortStr
函数并输出结果。sortStr
函数:
arr.sort((a, b) => { ... });
:对数组进行排序。a = a.toLowerCase();
和 b = b.toLowerCase();
:将字符串转换为小写,确保排序时不区分大小写。return a === b ? 0 : a > b ? 1 : -1;
:比较两个字符串的大小,返回排序结果。const stack = [arr.shift()];
:创建一个栈,并将排序后的第一个元素放入栈中。for (let str of arr) { ... }
:遍历数组,进行去重操作。const top = stack.at(-1).toLowerCase();
:获取栈顶元素并转换为小写。const add = str.toLowerCase();
:获取当前元素并转换为小写。if (top === add) continue;
:如果栈顶元素与当前元素相同,跳过。stack.push(str);
:否则将当前元素压入栈中。return stack.join(" ");
:将栈中的元素用空格连接成字符串并返回。假设输入字符串为"apple Banana apple orange banana"
:
["apple", "Banana", "apple", "orange", "banana"]
。["apple", "apple", "Banana", "banana", "orange"]
。["apple", "Banana", "orange"]
。"apple Banana orange"
。因此,程序输出为"apple Banana orange"
。
希望这个解释对您理解代码有所帮助!
以下是 Java代码 的详细中文注释和讲解:
import java.util.Arrays; // 引入Arrays类,用于数组操作
import java.util.LinkedList; // 引入LinkedList类,用于实现栈
import java.util.Scanner; // 引入Scanner类,用于读取控制台输入
import java.util.StringJoiner; // 引入StringJoiner类,用于拼接字符串
public class Main {
// 主函数,程序入口
public static void main(String[] args) {
Scanner sc = new Scanner(System.in); // 创建Scanner对象,用于读取控制台输入
String[] arr = sc.nextLine().split(" "); // 读取一行输入,并按空格分割成字符串数组
System.out.println(getResult(arr)); // 调用getResult函数并输出结果
}
// 算法入口,对字符串数组进行排序和去重
public static String getResult(String[] arr) {
// 对数组进行排序(不区分大小写)
Arrays.sort(arr, (a, b) -> a.toLowerCase().compareTo(b.toLowerCase()));
// 创建一个栈(使用LinkedList实现),并将排序后的第一个元素放入栈中
LinkedList<String> stack = new LinkedList<>();
stack.add(arr[0]);
// 遍历数组,进行去重操作
for (int i = 1; i < arr.length; i++) {
String s = arr[i]; // 获取当前元素
String top = stack.getLast().toLowerCase(); // 获取栈顶元素并转换为小写
String add = s.toLowerCase(); // 获取当前元素并转换为小写
if (top.equals(add)) continue; // 如果栈顶元素与当前元素相同,跳过
stack.add(s); // 否则将当前元素压入栈中
}
// 使用StringJoiner将栈中的元素用空格连接成字符串
StringJoiner sj = new StringJoiner(" ");
for (String s : stack) sj.add(s);
return sj.toString(); // 返回拼接后的字符串
}
}
引入类库:
import java.util.Arrays;
:引入Arrays
类,用于数组操作(如排序)。import java.util.LinkedList;
:引入LinkedList
类,用于实现栈。import java.util.Scanner;
:引入Scanner
类,用于读取控制台输入。import java.util.StringJoiner;
:引入StringJoiner
类,用于拼接字符串。主函数 main
:
Scanner sc = new Scanner(System.in);
:创建Scanner
对象,用于读取控制台输入。String[] arr = sc.nextLine().split(" ");
:读取一行输入,并按空格分割成字符串数组。System.out.println(getResult(arr));
:调用getResult
函数并输出结果。getResult
函数:
Arrays.sort(arr, (a, b) -> a.toLowerCase().compareTo(b.toLowerCase()));
:对数组进行排序,排序时不区分大小写。LinkedList stack = new LinkedList<>();
:创建一个栈(使用LinkedList
实现)。stack.add(arr[0]);
:将排序后的第一个元素放入栈中。for (int i = 1; i < arr.length; i++) { ... }
:遍历数组,进行去重操作。String top = stack.getLast().toLowerCase();
:获取栈顶元素并转换为小写。String add = s.toLowerCase();
:获取当前元素并转换为小写。if (top.equals(add)) continue;
:如果栈顶元素与当前元素相同,跳过。stack.add(s);
:否则将当前元素压入栈中。StringJoiner sj = new StringJoiner(" ");
:创建StringJoiner
对象,用于拼接字符串。for (String s : stack) sj.add(s);
:将栈中的元素逐个添加到StringJoiner
中。return sj.toString();
:返回拼接后的字符串。假设输入字符串为"apple Banana apple orange banana"
:
["apple", "Banana", "apple", "orange", "banana"]
。["apple", "apple", "Banana", "banana", "orange"]
。["apple", "Banana", "orange"]
。"apple Banana orange"
。因此,程序输出为"apple Banana orange"
。
LinkedList
实现栈,是一种常见的去重方法。StringJoiner
拼接字符串,可以避免手动处理空格。希望这个解释对您理解代码有所帮助!
以下是 Python代码 的详细中文注释和讲解:
# 输入获取
arr = input().split() # 读取一行输入,并按空格分割成列表
# 算法入口
def getResult():
# 对列表进行排序(不区分大小写)
arr.sort(key=lambda x: x.lower())
# 创建一个栈,并将排序后的第一个元素放入栈中
stack = [arr[0]]
# 遍历列表,进行去重操作
for i in range(1, len(arr)):
s = arr[i] # 获取当前元素
top = stack[-1].lower() # 获取栈顶元素并转换为小写
add = s.lower() # 获取当前元素并转换为小写
if top == add: # 如果栈顶元素与当前元素相同,跳过
continue
stack.append(s) # 否则将当前元素压入栈中
# 将栈中的元素用空格连接成字符串并返回
return " ".join(stack)
# 算法调用
print(getResult()) # 调用getResult函数并输出结果
输入获取:
arr = input().split()
:读取一行输入,并按空格分割成列表。getResult
函数:
arr.sort(key=lambda x: x.lower())
:对列表进行排序,排序时不区分大小写。stack = [arr[0]]
:创建一个栈,并将排序后的第一个元素放入栈中。for i in range(1, len(arr)): ...
:遍历列表,进行去重操作。top = stack[-1].lower()
:获取栈顶元素并转换为小写。add = s.lower()
:获取当前元素并转换为小写。if top == add: continue
:如果栈顶元素与当前元素相同,跳过。stack.append(s)
:否则将当前元素压入栈中。return " ".join(stack)
:将栈中的元素用空格连接成字符串并返回。算法调用:
print(getResult())
:调用getResult
函数并输出结果。假设输入字符串为"apple Banana apple orange banana"
:
["apple", "Banana", "apple", "orange", "banana"]
。["apple", "apple", "Banana", "banana", "orange"]
。["apple", "Banana", "orange"]
。"apple Banana orange"
。因此,程序输出为"apple Banana orange"
。
" ".join(stack)
拼接字符串,可以避免手动处理空格。希望这个解释对您理解代码有所帮助!
以下是 C++代码 和 C语言代码 的实现,并附上详细的中文注释和讲解:
#include
#include
#include
#include
using namespace std;
// 算法入口
string getResult(vector<string>& arr) {
// 对数组进行排序(不区分大小写)
sort(arr.begin(), arr.end(), [](const string& a, const string& b) {
string lowerA = a;
string lowerB = b;
transform(lowerA.begin(), lowerA.end(), lowerA.begin(), ::tolower);
transform(lowerB.begin(), lowerB.end(), lowerB.begin(), ::tolower);
return lowerA < lowerB;
});
// 创建一个栈,并将排序后的第一个元素放入栈中
vector<string> stack;
stack.push_back(arr[0]);
// 遍历数组,进行去重操作
for (int i = 1; i < arr.size(); i++) {
string s = arr[i]; // 获取当前元素
string top = stack.back(); // 获取栈顶元素
// 将栈顶元素和当前元素转换为小写进行比较
transform(top.begin(), top.end(), top.begin(), ::tolower);
string add = s;
transform(add.begin(), add.end(), add.begin(), ::tolower);
if (top == add) continue; // 如果栈顶元素与当前元素相同,跳过
stack.push_back(s); // 否则将当前元素压入栈中
}
// 将栈中的元素用空格连接成字符串
stringstream result;
for (int i = 0; i < stack.size(); i++) {
if (i > 0) result << " "; // 添加空格分隔符
result << stack[i];
}
return result.str(); // 返回拼接后的字符串
}
int main() {
string input;
getline(cin, input); // 读取一行输入
// 将输入按空格分割成数组
vector<string> arr;
stringstream ss(input);
string word;
while (ss >> word) {
arr.push_back(word);
}
// 调用算法并输出结果
cout << getResult(arr) << endl;
return 0;
}
输入获取:
getline(cin, input)
读取一行输入。stringstream
将输入按空格分割成vector
数组。getResult
函数:
sort
函数对数组进行排序,排序时不区分大小写。transform
函数将字符串转换为小写进行比较。vector
实现栈。stringstream
将栈中的元素用空格连接成字符串。主函数:
getResult
函数并输出结果。#include
#include
#include
#include
// 比较函数,用于排序(不区分大小写)
int compare(const void* a, const void* b) {
char* strA = *(char**)a;
char* strB = *(char**)b;
char lowerA[100], lowerB[100];
// 将字符串转换为小写
for (int i = 0; strA[i]; i++) lowerA[i] = tolower(strA[i]);
for (int i = 0; strB[i]; i++) lowerB[i] = tolower(strB[i]);
return strcmp(lowerA, lowerB);
}
// 算法入口
char* getResult(char** arr, int size) {
// 对数组进行排序(不区分大小写)
qsort(arr, size, sizeof(char*), compare);
// 创建一个栈,并将排序后的第一个元素放入栈中
char** stack = (char**)malloc(size * sizeof(char*));
int stackSize = 0;
stack[stackSize++] = arr[0];
// 遍历数组,进行去重操作
for (int i = 1; i < size; i++) {
char* s = arr[i]; // 获取当前元素
char* top = stack[stackSize - 1]; // 获取栈顶元素
// 将栈顶元素和当前元素转换为小写进行比较
char lowerTop[100], lowerS[100];
for (int j = 0; top[j]; j++) lowerTop[j] = tolower(top[j]);
for (int j = 0; s[j]; j++) lowerS[j] = tolower(s[j]);
if (strcmp(lowerTop, lowerS) == 0) continue; // 如果栈顶元素与当前元素相同,跳过
stack[stackSize++] = s; // 否则将当前元素压入栈中
}
// 计算结果字符串的长度
int resultLength = 0;
for (int i = 0; i < stackSize; i++) {
resultLength += strlen(stack[i]);
if (i < stackSize - 1) resultLength += 1; // 添加空格
}
// 分配内存并拼接结果字符串
char* result = (char*)malloc((resultLength + 1) * sizeof(char));
int index = 0;
for (int i = 0; i < stackSize; i++) {
strcpy(result + index, stack[i]);
index += strlen(stack[i]);
if (i < stackSize - 1) result[index++] = ' '; // 添加空格
}
result[index] = '\0'; // 添加字符串结束符
free(stack); // 释放栈的内存
return result;
}
int main() {
char input[1000];
fgets(input, sizeof(input), stdin); // 读取一行输入
// 将输入按空格分割成数组
char* arr[100];
int size = 0;
char* token = strtok(input, " \n");
while (token != NULL) {
arr[size++] = token;
token = strtok(NULL, " \n");
}
// 调用算法并输出结果
char* result = getResult(arr, size);
printf("%s\n", result);
free(result); // 释放结果字符串的内存
return 0;
}
输入获取:
fgets
读取一行输入。strtok
将输入按空格分割成字符串数组。getResult
函数:
qsort
函数对数组进行排序,排序时不区分大小写。tolower
函数将字符串转换为小写进行比较。主函数:
getResult
函数并输出结果。假设输入字符串为"apple Banana apple orange banana"
:
["apple", "Banana", "apple", "orange", "banana"]
。["apple", "apple", "Banana", "banana", "orange"]
。["apple", "Banana", "orange"]
。"apple Banana orange"
。因此,程序输出为"apple Banana orange"
。
希望这个解释对您理解代码有所帮助!