漏字文(C++)

题目描述:

有意避免使用某个或某几个特定字母的写成的文章称漏字文(英语lipogram,希腊语lipagrammatos,意为“失踪的字母”),漏字文可能在写作或文字游戏中出现。公元前5世纪希腊诗人里斐奥多鲁斯(Tryphiodorus)写的24卷史诗中,每一卷都省略希腊字母中的一个不同字母。

现在给你一段仅由空格和小写字母组成的字符串,请你找出其中最长的一段连续的漏字文,并输出漏字文的长度(即该段文字中字母的个数)。

输入格式:

输入共两行。 第一行一个数N(1≤N≤105),表示有N个由小写字母组成的单词。 第二行是一个字符串,有N个长度不超过10的单词,每个单词间用一个空格隔开。

输出格式:

一个整数,表示漏字文的长度。

输入样例:

在这里给出一组输入。例如:

9
the quick brown fox jumps over the lazy dog

输出样例:

在这里给出相应的输出。例如:

32

样例解释

“the quick brown fox jumps over the lazy dog”包含了所有的字母。 其中最长的漏字文是“the quick brown fox jumps over the lazy”,长度是32(即里面有32个字母)。这段文字没有字母d和g,符合漏字文的条件。

解题思路:

采用IPO思路构建代码:

(1)I和P:

核心解题思路1:将单词逻辑上存储,即只存储其属性

创建一个单词结构体,包括一个用于标记出现字母的整型数组(成员)和单词长度;

创建一个单词数组用于存储单词;

创建一个整型数组用于标记出现过的字母(全局)

for循环输入单词,获取并存储单词属性

(2)P和O:

核心解题思路2:遍历每一种可能的漏字文来得到最大漏字文长度,即

遍历尝试将每一个单词加入,若不“漏字”,则从头部开始退出单词,直到变回漏字文后,从尾部再次开始插入单词;

是否认为漏字文的判断功能用注释在下方进行说明;

(3)O:

cout << max_len ;

代码实现如下:

#include <iostream>
#include <string>
using namespace std;
​
struct word
{
    int word_book_char[26] = { 0 };//标记单词内出现过的字母
    int word_len;//存储单词的长度
};
​
struct word word_array[int(1e5)];//用于存储单词的属性
int book_char[26] = { 0 };//用于标记出现过的字母
​
int main()
{
    int n;
    cin >> n;//输入单词个数
    int max_len = 0, temp_len = 0;//最大漏字文长度,临时漏字文长度
    string temp_str;//临时字符串
    int i, j, head, sum;//sum用于判断是否“漏字”
    for (i = 0; i < n; i++)//输入单词并统计单词的属性
    {
        cin >> temp_str;
        //获取单词属性
        word_array[i].word_len = temp_str.size();//记录单词长度
        for (j = 0; j < word_array[i].word_len; j++)//记录单词内出现过的字母
        {
            word_array[i].word_book_char[temp_str[j] - 97] = 1;
        }
    }
    for (i = 0, head = i; i < n; i++)
    {
        temp_len += word_array[i].word_len;//累计长度
        //判断是否仍为漏字文功能的实现
        sum = 0;//sum用于统计出现的字母种类,每轮需要归零sum
        for (j = 0; j < 26; j++)//**每插入一个单词,遍历该单词的字母数组将其加到全局字母数组上**
        {
            book_char[j] += word_array[i].word_book_char[j];
            if (book_char[j])//**若全局字母数组元素>=1,则sum += 1**
            {
                sum += 1;
            }
        }
        //注意:每插入一个单词都需要判断是否仍为漏字文,若仍为漏字文则比较并记录最大长度
        if (sum == 26)//不“漏字”
        {
            while (sum == 26)//退出字母,直到重新变回“漏字文”
            {
                temp_len -= word_array[head].word_len;//**每退出一个单词都需要减去单词对应长度**
                for (j = 0; j < 26; j++)//每退出一个单词,用全局字母数组减去该单词的字母数组
                {
                    book_char[j] -= word_array[head].word_book_char[j];
                    if (book_char[j] == 0)//**若全局字母数组元素==0,则sum -= 1**
                    {
                        sum -= 1;//注意:不能立即break,因为可能一次性“消失”了多个字母
                    }
                }
                head++;
            }
        }
        //仍为“漏字文”
        if (temp_len > max_len)
        {
            max_len = temp_len;
        }
    }
    cout << max_len;
    return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

WitheredSakura_

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值