LeetCode数据结构_C语言题解系列-串
题目一.字符串中的第一个唯一字符
387. 字符串中的第一个唯一字符https://leetcode.cn/problems/first-unique-character-in-a-string/
给定一个字符串 s
,找到 它的第一个不重复的字符,并返回它的索引 。如果不存在,则返回 -1
。(s
只包含小写字母)
示例 :
输入: s = "leetcode" 输出: 0
1.思路分析
核心问题在于查找字符串中第一个仅出现过一次的字符:实现的思路多种多样:由于题干提示s仅包含小写字母,故笔者采用长为26的整型数组作为辅助数据结构,存储每个小写字母字符的出现次数。
程序采用二次循环即可,第一次循环遍历字符串s,统计出现字符。第二次循环遍历hash表,第一个出现次数为1的元素为结果。应该注意的是:遍历hash表的次序不是按hash表下标进行遍历,这样查找到的第一个键值为1的字符是出现次数为1、且字母在26个字母中最靠前的字符。
2.AC代码
int firstUniqChar(char * s){
int* flag=(int *)malloc(26*sizeof(int));
for(int i=0;i<26;i++) flag[i]=0;
for(int i=0;i<strlen(s);i++){
flag[s[i]-'a']++;
}
for(int i=0;i<strlen(s);i++){
if(flag[s[i]-'a']==1) return i;
}
return -1;
}
题目二.赎金信
383. 赎金信https://leetcode.cn/problems/ransom-note/
给你两个字符串:ransomNote 和 magazine ,判断 ransomNote 能不能由 magazine 里面的字符构成。如果可以,返回 true ;否则返回 false 。magazine 中的每个字符只能在 ransomNote 中使用一次。
示例 1:
输入:ransomNote = "a", magazine = "b" 输出:false示例 2:
输入:ransomNote = "aa", magazine = "ab" 输出:false
1.思路分析
本题解法也多种多样,笔者另辟蹊径,采用集合思想:由于magazine中的每个字符只能在 ransomNote 中使用一次,即ransomNote串 必然是magazine串的子集:(一定不是子串,因为顺序可以任意)
即ransomNote内每一个字符在magazine内必存在唯一映射
为了表示“唯一映射”性质,采用一个和magazine等长的数组flag作为辅助数据结构。采用二重循环:让ransomNote内每个字符在magazine内查询一轮,如果找到未曾被映射过的元素,将flag对应位置‘1’,以防止多次映射。
2.AC代码
bool canConstruct(char * ransomNote, char * magazine){
int cout=0;
int* flag=(int*)malloc(strlen(magazine)*sizeof(int));
for(int i=0;i<strlen(magazine);i++) flag[i]=0;
for(int i=0;i<strlen(ransomNote);i++){
for(int j=0;j<strlen(magazine);j++){
if(ransomNote[i]==magazine[j]&&flag[j]==0){
flag[j]=1;
cout=0;
break;
}
else cout++;
}
if(cout!=0) return false;
}
return true;
}
题目三.有效的字母异位词
242. 有效的字母异位词https://leetcode.cn/problems/valid-anagram/
给定两个字符串 s
和 t
,编写一个函数来判断 t
是否是 s
的字母异位词。
注意:若 s
和 t
中每个字符出现的次数都相同,则称 s
和 t
互为字母异位词。(s
和 t
仅包含小写字母)
示例 :
输入: s = "anagram", t = "nagaram" 输出: true
1.思路分析
由题干可知:s和t字符串都只包含小写字母,故可以采用两个hash表作为辅助数据结构flag1、flag2,将每个小写字母的出现次数统计出来,再遍历hash表,确保flag1与flag2每个对应位置相等后,返回true。否则返回false。
2.AC代码
bool isAnagram(char * s, char * t){
int* flag1=(int*)malloc(sizeof(int)*26);
int* flag2=(int*)malloc(sizeof(int)*26);
for(int i=0;i<26;i++){ flag1[i]=0;flag2[i]=0; }
for(int i=0;i<strlen(s);i++) flag1[s[i]-'a']++;
for(int i=0;i<strlen(t);i++) flag2[t[i]-'a']++;
for(int i=0;i<26;i++){
if(flag2[i]!=flag1[i]) return false;
}
return true;
}
相关文章
- Java实现 LeetCode 792 自定义字符串排序(暴力)
- Java实现 LeetCode 506 相对名次
- Java实现 LeetCode 427 建立四叉树
- Java实现 LeetCode 96 不同的二叉搜索树
- Java实现 LeetCode 87 扰乱字符串
- Java实现LeetCode 111. Minimum Depth of Binary Tree
- 【哈希表】LeetCode 49. 字母异位词分组【中等】
- LeetCode(31): 下一个排列
- LeetCode 3. 无重复字符的最长子串(C语言)
- LeetCode刷题笔录Add Binary
- leetcode 83. Remove Duplicates from Sorted List