算法入门经典 第五章

例题5-4 反片语

输入一些单词(以“#”为结束标志),找出所有满足如下条件的单词:该单词不能通过字母的重排,得到输入文本中的另一个单词。在判断是否满足条件是不分大小写,但是在输出时应保留输入时的大小写,按字典序进行排列(所有大写字母在所有小写字母前面)。

Sample input

ladder came tape soon leader acme RIDE lone Dreis peat
 ScAlE orb  eye  Rides dealer  NotE derail LaCeS  drIed
noel dire Disk mace Rob dries
#

Sample output

Disk
NotE
derail
drIed
eye
ladder
soon

分析

这道题的解法很多,最简化的方式就是使用map容器。想到使用“标准化”。整体思路:1.写一个标准化函数(实现大写字母转换为小写(tolower()函数),单词排序。注意使用const是为了不改变s的初值)2.两个vector容器(words,ans),一个map容器(cnt)words存储所有的单词map存储标准化后对应单词以及出现次数的值,相当于一个表格。words经过查表map,把对应的符合值给ans3.输出

代码:
#include<iostream>
#include<string>
#include<vector>
#include<algorithm>
#include<cctype>
#include<map>
using namespace std;
map<string,int>cnt;
vector<string>words;
//将单词s标准化
string repr(const string& s)//这个设计很巧妙 ,不改变原值
{
string ans=s;
for(int i=0;i<ans.size();i++)
ans[i]=tolower(ans[i]);//大写字母转化为小写
sort(ans.begin(),ans.end());
return ans;
}
int main()
{
int n=0;
string s;
while(cin>>s)
{
if(s[0]==‘#‘)break;
words.push_back(s);
string r=repr(s);
//cout<<r<<endl;
if(!cnt.count(r))cnt[r]=0;//count()如果键值存在返回1,否则返回0;初始化键值对应的值
cnt[r]++;//计算出现的次数 类似数组的初始化 没出现过所以先初始化0 出现过map键值对应的count++

}

vector<string>ans;
for(int i=0;i<words.size();i++)
if(cnt[repr(words[i])]==1)ans.push_back(words[i]);//查map表,将符合条件的单词放进ans容器
sort(ans.begin(),ans.end());
for(int i=0;i<ans.size();i++)
cout<<ans[i]<<endl;
return 0;
}

  

时间: 2024-10-09 10:25:06

算法入门经典 第五章的相关文章

算法入门经典-第五章 例题6-10 下落的树叶

给一颗二叉树,每个节点都有一个水平位置:左子结点在它的左边一个单位,右子节点在右 边一个单位.从左向右输出每个水平位置的所有节点的权值之和.如图所示,从左到右的三 个位置权和分别为 7,11,3,按照递归(先序)方式输入,用-1 表示空树. Sample Input  5 7 -1 6 -1 -1 3 -1 -1  8 2 9 -1 -1 6 5 -1 -1 12 -1 -1 3 7 -1 -1 -1 -1  Sample Output  Case 1: 7 11 3  Case 2: 9 7

算法入门经典-第五章 例题 5-5 集合栈计算机

The SetStack Computer Time limit: 3.000 seconds 题目是这样的: 有一个专门为了集合运算而设计的"集合栈"计算机.该机器有一个初始为空的栈,并且支持以下操作:PUSH:空集"{}"入栈DUP:把当前栈顶元素复制一份后再入栈UNION:出栈两个集合,然后把两者的并集入栈INTERSECT:出栈两个集合,然后把二者的交集入栈ADD:出栈两个集合,然后把先出栈的集合加入到后出栈的集合中,把结果入栈       每次操作后,输出

算法入门经典-第五章 例题5-7 丑数

#include<iostream> #include<vector> #include<queue> #include<set> using namespace std; typedef long long ll; const int coeff= {2,3,5}; int main() { //一些常见的优先队列,STL提供了更为简单的定义方法 //对于任意丑数x 则 2x,3x,5x也是丑数,判断一个丑数是否生成过 //每次取出最小的丑数,生成3个新的

算法入门经典-第五章 例题5-6 团体队列

题目背景 队列和优先级队列是大多数计算机科学家都知道的数据结构.但是团队队列却不被人熟知,尽管在生活中经常出现.比如,午餐时间的食堂门口的队列就是一个团队队列.在一个团队队列中,每个元素属于一个团队.如果一个元素进入一个队列,它首先从头到尾地搜寻这个队列--检查是否它的队友(在同一个团队称之为队友)也在这个队列里.如果有,它就排在它队友的后面(:-D就是插队咯~~).如果没有,它就排在整个队列的最后,成为新的最后一名(/(ㄒoㄒ)/~真是不幸).在普通队列中出队是这样的:元素从头到尾的被处理,按

算法入门经典第六章 例题6-14 Abbott的复仇(Abbott&#39;s Revenge)BFS算法实现

Sample Input 3 1 N 3 3 1 1 WL NR * 1 2 WLF NR ER * 1 3 NL ER * 2 1 SL WR NF * 2 2 SL WF ELF * 2 3 SFR EL * 0 Sample Output (3,1) (2,1) (1,1) (1,2) (2,2) (2,3) (1,3) (1,2) (1,1) (2,1) (2,2) (1,2) (1,3) (2,3) (3,3) 析 题目的大意是,输入起点,离开起点时的朝向和终点,求一条最短路. 每一个

算法入门经典-第七章 例题7-4-1 拓展 n皇后问题 回溯法

实际上回溯法有暴力破解的意思在里面,解决一个问题,一路走到底,路无法通,返回寻找另   一条路. 回溯法可以解决很多的问题,如:N皇后问题和迷宫问题. 一.概念 回溯算法实际类似枚举的搜索尝试过程,主要是在搜索尝试过程中寻找问题的解,当发现不满足条件的时候,就回溯返回,尝试别的路径. 百度解释:回溯法(探索与回溯法)是一种选优搜索法,又称为试探法,按选优条件向前搜索,以达到目标.但当探索到某一步时,发现原先选择并不优或达不到目标,就退回一步重新选择,这种走不通就退回再走的技术为回溯法,而满足回溯

算法入门经典-第七章 例题7-2 八皇后问题

原本利用回溯思想解决的经典八皇后问题,其实也是可以用递归解决的~ 八皇后的递归解决思路: 从第一行开始,依次判断0~8列的哪一列可以放置Queen,这样就确定了该行的Queen的位置,然后行数递增,继而递归实现下一行的判断,依次类推直到行数增加到8(行数从0开始的),此时为递归-----归的条件,即表示一种八皇后的解决方法完成,打印结果:之后进行下一种解决方法的寻找,大致思路个人理解是这样 noDanger(row,j,(*chess)[8])函数是判断第row行第j列是否可以放置Queen #

算法入门经典-第七章 例题7-2-2 可重集的排列

可重:如果问题变成输入数组p,并按字典序输出数组A个元素的所有全排列,则需要修改代码集的全排列 // Rujia Liu #include<cstdio> #include<algorithm> using namespace std; int P[100], A[100]; // 输出数组P中元素的全排列.数组P中可能有重复元素 void print_permutation(int n, int* P, int* A, int cur) { if(cur == n) { for(

算法入门经典第六章 例题6-5 移动盒子

例题 6-5 移动盒子(Boxes in a Line, UVa127675) 问题 给定一行盒子,从左到右编号依次为1,2,...,n.可以执行以下命令: 1 X Y 把盒子 X 移动到 Y 的左边(如果已经在左边,忽略此命令) 2 X Y 把盒子 X 移动到 Y 右边(如果X已经在Y的右边,忽略此命令) 3 X Y交换 X 和 Y 的位置 4 把整个顺序颠倒 指令保证合法,即X 不等于 Y, 输入包含不超过10组数据,每组第一行为盒子的数目n和指令的数目m(1<=n,m<=100000).

算法入门经典-第七章 例题7-1 除法

除法输入正整数n,按从小到大的顺序输出所有形如abcde/fghij=n的表达式,其中a~j恰好为数字0~9的一个排列,2<=n<=79. 样例输入: 62 样例输出: 79546/01238=62 94736/01528=62 #include<stdio.h> #include<string.h> int main() { int n; //x/y=n x用abcde表示,若整除n,求出y,而后用fghij表示Y,看是否重复数字 while(~scanf("