wordpress多域名配置文件网站排名优化公司
华为OD机试 2024E卷题库疯狂收录中,刷题点这里
专栏导读
本专栏收录于《华为OD机试真题(Python/JS/C/C++)》。
刷的越多,抽中的概率越大,私信哪吒,备注华为OD,加入华为OD刷题交流群,每一题都有详细的答题思路、详细的代码注释、3个测试用例、为什么这道题采用XX算法、XX算法的适用场景,发现新题目,随时更新,全天CSDN在线答疑。
一、题目描述
有一个文件,包含以一定规则写作的文本,请统计文件中包含的文本数量。
规则如下:
1、文本以";“分隔,最后一条可以没有”;",但空文本不能算语句,比如"COMMAND A;“只能算一条语句。注意,无字符/空白字符Q/制表符等操作"空文本”;
2、文本可以跨行,比如下面,是一条文本,而不是三条;
COMMAND A
AND
COMMAND B;
文本支持字符串,字符串为成对的单引号(‘)或者成对的双引号("),字符串中可能出现用转义字符()处理的单双引号(‘your input is’”)和转义字符串本身,比如
COMMAND A "Say \"hello\"";
支持注释,可以出现在字符串之外的任意位置注释以"—"开头,到换行结束,比如:
COMMAND A; —this is comment
COMMAND —comment
A AND COMMAND B;
注意 字符串Q 内的“—”,不是注释。
二、输入描述
文本文件
三、输出描述
包含的文本数量
四、测试用例
测试用例1:
1、输入
COMMAND A;
COMMAND B;
COMMAND C; — This is a comment
COMMAND D; — Another comment
2、输出
4
3、说明
本例中的文件内容有4个命令,每个命令都以分号结尾。
尽管第三行和第四行后面有注释,注释部分不会影响命令的统计。
因此,总共4条有效命令。
测试用例2:
1、输入
COMMAND A;
COMMAND B
AND COMMAND C;
COMMAND “D"Text”";
— Entire line is a comment
COMMAND E; — Comment at the end
2、输出
4
3、说明
第一行 COMMAND A; 是一条有效命令。
第二行和第三行合并构成一条跨行命令 COMMAND B AND COMMAND C;。
第四行 COMMAND “D"Text”"; 是一条有效命令,其中 " 表示转义字符,表示字符串中的双引号。
第五行是一个注释,应该被忽略。
第六行 COMMAND E; 是一条有效命令,尽管有注释。
最终,共有4条有效命令。
五、解题思路
程序会检查文件内容中的注释,并将这些注释移除。注释是以 “—” 开头,直到该行结束。需要注意的是,程序会确保只移除字符串之外的注释,即在字符串内的 “—” 不会被视为注释。这一步是为了避免注释内容干扰命令的统计。
程序会根据分号(;)将内容分割成多个部分,每个部分代表一个潜在的命令。
对于每个分割出的部分,程序会去除首尾空白符,并检查内容是否为空。只有非空的部分才会被计数为有效命令。这一步是为了确保空白命令或无效的命令不会被错误地计入。
程序会输出统计得到的有效命令数量。这个数量即为文件中符合规则的命令的总数。
六、Python算法源码
import sysdef is_escaped(line, index):"""判断当前位置的字符是否被转义:param line: 当前处理的行字符串:param index: 当前字符的索引:return: 如果字符被转义,返回True;否则返回False"""backslash_count = 0index -= 1 # 检查当前字符前面的字符while index >= 0 and line[index] == '\\':backslash_count += 1index -= 1return backslash_count % 2 != 0 # 如果反斜杠数量为奇数,则字符被转义def find_comment_index(line):"""找到注释的起始位置,忽略字符串内的注释符:param line: 当前处理的行字符串:return: 注释符的索引,如果没有注释,返回-1"""in_single_quote = False # 是否在单引号字符串内in_double_quote = False # 是否在双引号字符串内for i, ch in enumerate(line):if ch == '\'' and not is_escaped(line, i):in_single_quote = not in_single_quote # 切换单引号状态elif ch == '"' and not is_escaped(line, i):in_double_quote = not in_double_quote # 切换双引号状态elif ch == '—' and not in_single_quote and not in_double_quote:return i # 找到不在字符串内的注释符return -1 # 没有找到注释符def main():count = 0 # 有效命令计数current_text = [] # 当前命令的内容列表in_single_quote = False # 是否在单引号字符串内in_double_quote = False # 是否在双引号字符串内for line in sys.stdin:line = line.rstrip('\n') # 移除行尾的换行符if not line:break # 输入空行结束输入# 处理注释:找到注释符的位置并截断comment_index = find_comment_index(line)if comment_index != -1:line = line[:comment_index]i = 0 # 当前字符索引while i < len(line):ch = line[i] # 当前字符# 处理引号,切换状态if ch == '\'' and not is_escaped(line, i):in_single_quote = not in_single_quoteelif ch == '"' and not is_escaped(line, i):in_double_quote = not in_double_quote# 处理文本结束符';'if ch == ';' and not in_single_quote and not in_double_quote:if ''.join(current_text).strip(): # 如果当前命令非空count += 1 # 有效命令数加一current_text = [] # 重置当前命令内容else:current_text.append(ch) # 添加字符到当前命令i += 1 # 移动到下一个字符current_text.append('\n') # 保留换行符以支持跨行命令# 处理最后一个可能没有分号的文本final_text = ''.join(current_text).strip()if final_text and not final_text.startswith('—'):count += 1 # 如果最后的文本非空且不是注释,计数加一print(count) # 输出有效命令数量if __name__ == "__main__":main()
七、JavaScript算法源码
const readline = require('readline');/*** 判断当前位置的字符是否被转义* @param {string} line - 当前处理的行字符串* @param {number} index - 当前字符的索引* @returns {boolean} 如果字符被转义,返回true;否则返回false*/
function isEscaped(line, index) {let backslashCount = 0;index -= 1; // 检查当前字符前面的字符while (index >= 0 && line[index] === '\\') {backslashCount++;index--;}return backslashCount % 2 !== 0; // 如果反斜杠数量为奇数,则字符被转义
}/*** 找到注释的起始位置,忽略字符串内的注释符* @param {string} line - 当前处理的行字符串* @returns {number} 注释符的索引,如果没有注释,返回-1*/
function findCommentIndex(line) {let inSingleQuote = false; // 是否在单引号字符串内let inDoubleQuote = false; // 是否在双引号字符串内for (let i = 0; i < line.length; i++) {const ch = line[i];if (ch === '\'' && !isEscaped(line, i)) {inSingleQuote = !inSingleQuote; // 切换单引号状态} else if (ch === '"' && !isEscaped(line, i)) {inDoubleQuote = !inDoubleQuote; // 切换双引号状态} else if (ch === '—' && !inSingleQuote && !inDoubleQuote) {return i; // 找到不在字符串内的注释符}}return -1; // 没有找到注释符
}// 创建读取接口,用于逐行读取输入
const rl = readline.createInterface({input: process.stdin,output: process.stdout,terminal: false
});let count = 0; // 有效命令计数
let currentText = []; // 当前命令的内容数组
let inSingleQuote = false; // 是否在单引号字符串内
let inDoubleQuote = false; // 是否在双引号字符串内// 监听每一行的输入
rl.on('line', (line) => {if (line === '') {rl.close(); // 输入空行结束输入return;}// 处理注释:找到注释符的位置并截断const commentIndex = findCommentIndex(line);if (commentIndex !== -1) {line = line.substring(0, commentIndex);}for (let i = 0; i < line.length; i++) {const ch = line[i];// 处理引号,切换状态if (ch === '\'' && !isEscaped(line, i)) {inSingleQuote = !inSingleQuote;} else if (ch === '"' && !isEscaped(line, i)) {inDoubleQuote = !inDoubleQuote;}// 处理文本结束符';'if (ch === ';' && !inSingleQuote && !inDoubleQuote) {if (currentText.join('').trim().length > 0) { // 如果当前命令非空count++; // 有效命令数加一currentText = []; // 重置当前命令内容}} else {currentText.push(ch); // 添加字符到当前命令}}currentText.push('\n'); // 保留换行符以支持跨行命令
});// 输入结束后处理
rl.on('close', () => {// 处理最后一个可能没有分号的文本const finalText = currentText.join('').trim();if (finalText.length > 0 && !finalText.startsWith('—')) {count++; // 如果最后的文本非空且不是注释,计数加一}console.log(count); // 输出有效命令数量
});
八、C算法源码
#include <stdio.h>
#include <string.h>
#include <stdbool.h>#define MAX_LINE_LENGTH 1000/*** 判断当前位置的字符是否被转义* @param line 当前处理的行字符串* @param index 当前字符的索引* @return 如果字符被转义,返回true;否则返回false*/
bool is_escaped(char *line, int index) {int backslash_count = 0;index--; // 检查当前字符前面的字符while (index >= 0 && line[index] == '\\') {backslash_count++;index--;}return backslash_count % 2 != 0; // 如果反斜杠数量为奇数,则字符被转义
}/*** 找到注释的起始位置,忽略字符串内的注释符* @param line 当前处理的行字符串* @return 注释符的索引,如果没有注释,返回-1*/
int find_comment_index(char *line) {bool in_single_quote = false; // 是否在单引号字符串内bool in_double_quote = false; // 是否在双引号字符串内int len = strlen(line);for (int i = 0; i < len; i++) {char ch = line[i];if (ch == '\'' && !is_escaped(line, i)) {in_single_quote = !in_single_quote; // 切换单引号状态} else if (ch == '"' && !is_escaped(line, i)) {in_double_quote = !in_double_quote; // 切换双引号状态} else if (ch == '—' && !in_single_quote && !in_double_quote) {return i; // 找到不在字符串内的注释符}}return -1; // 没有找到注释符
}int main() {char line[MAX_LINE_LENGTH]; // 用于存储每一行输入int count = 0; // 有效命令计数char current_text[MAX_LINE_LENGTH * 10] = ""; // 当前命令的内容字符串// 逐行读取输入while (fgets(line, sizeof(line), stdin)) {// 移除末尾的换行符size_t len = strlen(line);if (len > 0 && line[len - 1] == '\n') {line[len - 1] = '\0';}if (strlen(line) == 0) {break; // 输入空行结束输入}// 处理注释:找到注释符的位置并截断int comment_index = find_comment_index(line);if (comment_index != -1) {line[comment_index] = '\0';}// 遍历每个字符for (int i = 0; i < strlen(line); i++) {char ch = line[i];// 处理引号,切换状态if (ch == '\'' && !is_escaped(line, i)) {// 切换单引号状态// 在C语言中,单引号用于字符,通常不会跨多个字符// 此处假设与Java代码逻辑一致// 实际应用中可能需要调整} else if (ch == '"' && !is_escaped(line, i)) {// 切换双引号状态// 同上}// 需要重新处理引号状态bool in_single_quote = false;bool in_double_quote = false;for (int j = 0; j <= i; j++) {if (line[j] == '\'' && !is_escaped(line, j)) {in_single_quote = !in_single_quote;} else if (line[j] == '"' && !is_escaped(line, j)) {in_double_quote = !in_double_quote;}}// 处理文本结束符';'if (ch == ';' && !in_single_quote && !in_double_quote) {// 检查current_text是否非空bool non_empty = false;for (int k = 0; k < strlen(current_text); k++) {if (current_text[k] != ' ' && current_text[k] != '\t' && current_text[k] != '\n') {non_empty = true;break;}}if (non_empty) {count++; // 有效命令数加一current_text[0] = '\0'; // 重置当前命令内容}} else {// 添加字符到当前命令int current_len = strlen(current_text);if (current_len < sizeof(current_text) - 1) { // 防止溢出current_text[current_len] = ch;current_text[current_len + 1] = '\0';}}}// 添加换行符以支持跨行命令strcat(current_text, "\n");}// 处理最后一个可能没有分号的文本// 移除前导空白char *final_text = current_text;while (*final_text == ' ' || *final_text == '\t' || *final_text == '\n') {final_text++;}if (strlen(final_text) > 0 && final_text[0] != '—') {count++; // 如果最后的文本非空且不是注释,计数加一}printf("%d\n", count); // 输出有效命令数量return 0;
}
九、C++算法源码
#include <iostream>
#include <string>using namespace std;/*** 判断当前位置的字符是否被转义* @param line 当前处理的行字符串* @param index 当前字符的索引* @return 如果字符被转义,返回true;否则返回false*/
bool is_escaped(const string &line, int index) {int backslash_count = 0;index--; // 检查当前字符前面的字符while (index >= 0 && line[index] == '\\') {backslash_count++;index--;}return backslash_count % 2 != 0; // 如果反斜杠数量为奇数,则字符被转义
}/*** 找到注释的起始位置,忽略字符串内的注释符* @param line 当前处理的行字符串* @return 注释符的索引,如果没有注释,返回-1*/
int find_comment_index(const string &line) {bool in_single_quote = false; // 是否在单引号字符串内bool in_double_quote = false; // 是否在双引号字符串内for (int i = 0; i < line.length(); i++) {char ch = line[i];if (ch == '\'' && !is_escaped(line, i)) {in_single_quote = !in_single_quote; // 切换单引号状态} else if (ch == '"' && !is_escaped(line, i)) {in_double_quote = !in_double_quote; // 切换双引号状态} else if (ch == '—' && !in_single_quote && !in_double_quote) {return i; // 找到不在字符串内的注释符}}return -1; // 没有找到注释符
}int main() {int count = 0; // 有效命令计数string current_text = ""; // 当前命令的内容字符串string line; // 用于存储每一行输入// 逐行读取输入while (getline(cin, line)) {if (line.empty()) {break; // 输入空行结束输入}// 处理注释:找到注释符的位置并截断int comment_index = find_comment_index(line);if (comment_index != -1) {line = line.substr(0, comment_index);}// 遍历每个字符for (size_t i = 0; i < line.length(); i++) {char ch = line[i];// 处理引号,切换状态if (ch == '\'' && !is_escaped(line, i)) {// 切换单引号状态// 在C++中,单引号用于字符,通常不会跨多个字符// 此处假设与Java代码逻辑一致// 实际应用中可能需要调整} else if (ch == '"' && !is_escaped(line, i)) {// 切换双引号状态// 同上}// 需要重新处理引号状态bool in_single_quote = false;bool in_double_quote = false;for (size_t j = 0; j <= i; j++) {if (line[j] == '\'' && !is_escaped(line, j)) {in_single_quote = !in_single_quote;} else if (line[j] == '"' && !is_escaped(line, j)) {in_double_quote = !in_double_quote;}}// 处理文本结束符';'if (ch == ';' && !in_single_quote && !in_double_quote) {if (current_text.find_first_not_of(" \t\n") != string::npos) { // 如果当前命令非空count++; // 有效命令数加一current_text = ""; // 重置当前命令内容}} else {current_text += ch; // 添加字符到当前命令}}// 添加换行符以支持跨行命令current_text += '\n';}// 处理最后一个可能没有分号的文本// 移除前导空白size_t start = current_text.find_first_not_of(" \t\n");if (start != string::npos) {string final_text = current_text.substr(start);if (!final_text.empty() && final_text[0] != '—') {count++; // 如果最后的文本非空且不是注释,计数加一}}cout << count << endl; // 输出有效命令数量return 0;
}
🏆下一篇:华为OD机试真题 - 简易内存池(Python/JS/C/C++ 2024 E卷 200分)
🏆本文收录于,华为OD机试真题(Python/JS/C/C++)
刷的越多,抽中的概率越大,私信哪吒,备注华为OD,加入华为OD刷题交流群,每一题都有详细的答题思路、详细的代码注释、3个测试用例、为什么这道题采用XX算法、XX算法的适用场景,发现新题目,随时更新,全天CSDN在线答疑。