LintCode刷题指南:字符串处理(C++,Python)
题目:两个字符串是变位词
题目难度:简单
题目描述:
写出一个函数 anagram(s, t)
判断两个字符串是否可以通过改变字母的顺序变成一样的字符串。
解题思路:
C++:引入哈希的思维,这道题就迎刃而解了。
C++ Code:
class Solution {
public:
/**
* @param s: The first string
* @param b: The second string
* @return true or false
*/
bool anagram(string s, string t) {
// write your code here
int dic[58];
for (int i = 0; i < 58; i++)
dic[i] = 0;
for ( int i = 0; i < s.size(); i++ )
{
if (s[i] == ' ')
continue;
int index = s[i] - 'A';
dic[index]++;
}
for ( int i = 0; i < t.size(); i++ )
{
if (t[i] == ' ')
continue;
int index = t[i] - 'A';
dic[index]--;
}
for ( int i = 0; i < 58; i++ )
{
if (i==57 && dic[i]==0)
return true;
if (dic[i] == 0)
continue;
else
return false;
}
}
};
Python:利用Python的list()方法与sort()方法就可以成功地解决这道问题。
Python Code:
class Solution:
"""
@param s: The first string
@param b: The second string
@return true or false
"""
def anagram(self, s, t):
# write your code here
a = list(s)
b = list(t)
a.sort()
b.sort()
if a == b:
return True
else:
return False
题目:比较字符串
题目难度:简单
题目描述:
比较两个字符串A和B,确定A中是否包含B中所有的字符。字符串A和B中的字符都是大写字母。
解题思路:
C++:与第一道题几乎一样的哈希思路。
C++ Code:
class Solution {
public:
/**
* @param A: A string includes Upper Case letters
* @param B: A string includes Upper Case letter
* @return: if string A contains all of the characters in B return true
* else return false
*/
bool compareStrings(string A, string B) {
// write your code here
int dic[26];
int index;
for (int i = 0; i < 26; i++)
dic[i] = 0;
for (int i = 0; i < A.size(); i++) {
if (A[i] == ' ')
continue;
index = A[i] - 'A';
dic[index]++;
}
for (int i = 0; i < B.size(); i++) {
if (B[i] == ' ')
continue;
index = B[i] - 'A';
dic[index]--;
}
for (int i = 0; i < 26; i++) {
if (dic[i] < 0)
return false;
if (i == 25 && dic[i] >= 0)
return true;
}
}
};
Python:利用Python中的list()方法与index()方法,将B中的字符在A中逐个比对,每一次将A中对应的字符删除,循环这个过程。
Python Code:
class Solution:
"""
@param A : A string includes Upper Case letters
@param B : A string includes Upper Case letters
@return : if string A contains all of the characters in B return True else return False
"""
def compareStrings(self, A, B):
# write your code here
a = list(A)
b = list(B)
for n in b:
if n in a:
index = a.index(n)
del a[index]
continue
else:
return False
return True
题目:字符串查找
题目难度:简单
题目描述:
对于一个给定的 source 字符串和一个 target 字符串,你应该在 source 字符串中找出 target 字符串出现的第一个位置(从0开始)。如果不存在,则返回-1。
解题思路:
C++:通过一个简单的二层循环嵌套进行比对即可解决此题,需要注意的是处理NULL情况。
C++ Code:
class Solution {
public:
/**
* Returns a index to the first occurrence of target in source,
* or -1 if target is not part of source.
* @param source string to be scanned.
* @param target string containing the sequence of characters to match.
*/
int strStr(const char *source, const char *target) {
// write your code here
if (source == NULL || target == NULL)
return -1;
int index, i;
int ssize = strlen(source);
int tsize = strlen(target);
if (ssize < tsize)
return -1;
for (index = 0; index <= ssize - tsize; index++)
{
for (i = 0; i <= tsize - 1; i++)
{
if (source[i + index] != target[i])
break;
}
if (i == tsize)
return index;
}
return -1;
}
};
Python:和C++的思路是大致相同的,但是可以运用Python中的字符串截取方法,代码比C++更简短,同样需要注意处理null情况(Python中为None)。
Python Code:
class Solution:
def strStr(self, source, target):
# write your code here
index = 0
if source is None or target is None:
return -1
if len(source) < len(target):
return -1
if source == target:
return 0
while index <= len(source) - len(target):
if source[index: index + len(target)] == target:
return index
if index == len(source) - len(target) and source != target:
return -1
index += 1
题目:乱序字符串
题目难度:中等
题目描述:
给出一个字符串数组S,找到其中所有的乱序字符串(Anagram)。如果一个字符串是乱序字符串,那么他存在一个字母集合相同,但顺序不同的字符串也在S中。
解题思路:
C++:先将字符串数组中的字符串都进行排序,然后运用unordered_map的特性来解决问题,值得一提的是,如果在排序方法中运用O(n^2)的方法,是会判定超时的。
C++ Code:
class Solution {
public:
/**
* @param strs: A list of strings
* @return: A list of strings
*/
void sort(string &input) {
int count[26];
int index;
for (int i = 0; i < 26; i++) {
count[i] = 0;
}
for (int i = 0; i < input.length(); i++) {
index = input[i] - 'a';
count[index]++;
}
input = "";
for (int i = 0; i < 26; i++) {
for (int j = 0; j < count[i]; j++) {
input += (char)('a' + i);
}
}
}
vector<string> anagrams(vector<string> &strs) {
// write your code here
vector<string> result;
vector<string> mystrs = strs;
for (int i = 0; i < mystrs.size(); i++) {
sort (mystrs[i]);
}
unordered_map<string, int> dic;
for (int i = 0; i < mystrs.size(); i++) {
if (dic.find(mystrs[i]) == dic.end())
dic[mystrs[i]] = 1;
else
dic[mystrs[i]]++;
}
for (int i = 0; i < mystrs.size(); i++) {
if (dic[mystrs[i]] == 1)
continue;
else
result.push_back(strs[i]);
}
return result;
}
};
Python:在思路上和C++解法并没有太大区别,但是由于Python语言本身的一些特性,可以让代码量相较于C++版本的解法大幅减少,运用Python中的字典类型与sorted()方法可以很简洁地解出这道题。(注:运用sort()方法也可以,但是sort()方法本身会改变list的值,会让代码量略微增多)
Python Code:
class Solution:
# @param strs: A list of strings
# @return: A list of strings
def anagrams(self, strs):
# write your code here
dic = {}
result = []
for string in strs:
sortedstr = "".join(sorted(string));
dic[sortedstr] = [string] if sortedstr not in dic else dic[sortedstr] + [string]
for key in dic:
result += dic[key] if len(dic[key]) >= 2 else []
return result
题目:最长公共子串
题目难度:中等
题目描述:
给出两个字符串,找到最长公共子串,并返回其长度。
解题思路:
C++:这道题固然是可以用遍历的方法硬解出来的,但是那样的复杂度是非常不令人满意的,这里比较好的方法是运用动态规划的思想来解答,假设在求最长公共子串对的过程中,A中的子串中最后一个字符的位置为i,B中的子串中最后一个字符的位置为j,实际上就可以把“分别以A[i]与B[j]作为最后一个字符时最长公共字串的长度是多少”当作动态规划中的子问题,设分别以A[i]与B[j]作为最后一个字符时最长公共字串的长度为longestCommonSubstring[i][j],不难得出longerstCommonSubstring[i][j] = (A[i] == B[j] ? longestCommonSubstring[i - 1][j - 1] + 1 : 0)的推导关系,这样就可以以动态规划的思想来解答该题了。
C++ Code:
class Solution {
public:
/*
* @param A: A string
* @param B: A string
* @return: the length of the longest common substring.
*/
int longestCommonSubstring(string A, string B) {
// write your code here
if (A == "" || B == "")
return 0;
int sizeA = A.size();
int sizeB = B.size();
int longest = 0;
vector<vector<int> > list(sizeA, vector<int>(sizeB, 0));
int initIndex = 0;
for (int i = 0; i < sizeB; i++) {
list[initIndex][i] = (A[initIndex] == B[i] ? 1 : 0);
}
for (int i = 0; i < sizeA; i++) {
list[i][initIndex] = (A[i] == B[initIndex] ? 1 : 0);
}
for (int i = 1; i < sizeA; i++) {
for (int j = 1; j < sizeB; j++) {
list[i][j] = (A[i] == B[j] ? list[i - 1][j - 1] + 1 : 0);
}
}
for (int i = 0; i < sizeA; i++) {
for (int j = 0; j < sizeB; j++) {
if (longest < list[i][j])
longest = list[i][j];
}
}
return longest;
}
};
Python:解题思路与C++版本相同,直接贴代码。
Python Code:
class Solution:
"""
@param: A: A string
@param: B: A string
@return: the length of the longest common substring.
"""
def longestCommonSubstring(self, A, B):
# write your code here
if (len(A) == 0 or len(B) == 0):
return 0
longest = 0
list = [[0 for i in range(len(B))] for j in range(len(A))]
for i in range(len(B)):
if A[0] == B[i]:
list[0][i] = 1
for i in range(len(A)):
if A[i] == B[0]:
list[i][0] = 1
for i in range(1, len(A)):
for j in range(1, len(B)):
if A[i] == B[j]:
list[i][j] = list[i - 1][j - 1] + 1
for i in range(len(A)):
for j in range(len(B)):
if list[i][j] > longest:
longest = list[i][j]
return longest
题目:最长公共前缀
题目难度:中等
题目描述:
给k个字符串,求出他们的最长公共前缀(LCP)。
解题思路:
C++:没有什么难点,注意判断几个特殊情况即可,例如传入的字符串个数为0,或传入的字符串中存在长度为0的字符串。
C++ Code:
class Solution {
public:
/*
* @param strs: A list of strings
* @return: The longest common prefix
*/
string longestCommonPrefix(vector<string> strs) {
// write your code here
string LCP;
if (strs.size() == 0)
return LCP;
for (int i = 0; i < strs[0].length(); i ++) {
for (int j = 1; j < strs.size(); j++) {
if (strs[j] == "")
return LCP;
if (strs[j].length() < i + 1)
return LCP;
if (strs[0][i] != strs[j][i])
return LCP;
}
LCP += strs[0][i];
}
return LCP;
}
};
Python:与C++的解题思路一致,直接上代码:
Python Code:
class Solution:
"""
@param: strs: A list of strings
@return: The longest common prefix
"""
def longestCommonPrefix(self, strs):
# write your code here
if len(strs) == 0:
return ""
if len(strs) == 1:
return strs[0]
minlength = min([len(s) for s in strs])
for i in range(minlength):
for j in strs:
if strs[0][i] != j[i]:
return strs[0][0: i]
return strs[0][0: minlength]
题目:转换字符串到整数
题目难度:困难
题目描述:
实现atoi这个函数,将一个字符串转换为整数。如果没有合法的整数,返回0。如果整数超出了32位整数的范围,返回INT_MAX(2147483647)如果是正整数,或者INT_MIN(-2147483648)如果是负整数。
解题思路:
C++:此题的难点主要在于需要考虑很多种情况,非常容易遗漏,需要考虑的情况有:传入的字符串长度为零;字符串前几位为‘ ’;正负号情况;字符串中间出现的非数字;数字大于INT_MAX或小于INT_MIN。
C++ Code:
class Solution {
public:
/*
* @param str: A string
* @return: An integer
*/
int atoi(string str) {
// write your code here
int index = 0;
while (str[index] == ' ')
index++;
int number = 0, sign = 1;
if (str[index] == '-' || str[index] == '+') {
sign = str[index] == '-' ? -1: 1;
index++;
}
for (; index < str.size(); index++) {
if (str[index] >= '0' && str[index] <= '9') {
if (number > INT_MAX / 10 || (number == INT_MAX / 10 && str[index] - '0' > 7))
return sign == 1 ? INT_MAX: INT_MIN;
number = number * 10 + (str[index] - '0');
}
else
return number * sign;
}
return number * sign;
}
};
Python:解题思路与C++一致。
Python Code:
class Solution:
"""
@param: str: A string
@return: An integer
"""
def atoi(self, str):
# write your code here
index, number, sign = 0, 0, 1
intmax, intmin = (1 << 31) - 1, -1 << 31
if str == "":
return number
while str[index] == ' ':
index += 1;
if str[index] == '-' or str[index] == '+':
if str[index] == '-':
sign = -1
index += 1
while index < len(str) and str[index] >= '0' and str[index] <= '9':
if number > intmax / 10 or (number == intmax / 10 and ord(str[index]) - ord('0') > 7):
return intmax if sign == 1 else intmin
number = number * 10 + ord(str[index]) - ord('0')
index += 1
return number * sign
备注:本人非常乐意分享我的文章,转载请注明我的博客地址:http://www.cnblogs.com/matthewli/与原文地址:http://www.cnblogs.com/matthewli/p/7376738.html,谢谢!
LintCode刷题指南:字符串处理(C++,Python)的更多相关文章
- LeetCode刷题指南(字符串)
作者:CYC2018 文章链接:https://github.com/CyC2018/CS-Notes/blob/master/docs/notes/Leetcode+%E9%A2%98%E8%A7% ...
- lintcode 刷题 by python 总结(1)
博主之前在学习 python 的数据结构与算法的基础知识,用的是<problem-solving-with-algorithms-and-data-structure-using-python& ...
- LeetCode 刷题指南(1):为什么要刷题
虽然刷题一直饱受诟病,不过不可否认刷题确实能锻炼我们的编程能力,相信每个认真刷题的人都会有体会.现在提供在线编程评测的平台有很多,比较有名的有 hihocoder,LintCode,以及这里我们关注的 ...
- LeetCode刷题总结-字符串篇
本文梳理对LeetCode上有关字符串习题的知识点,并给出对应的刷题建议.本文建议刷题的总数为32题.具体知识点如下图: 1.回文问题 题号:5. 最长回文子串,难度中等 题号:214. 最短回文串, ...
- leetcode刷题指南
转载自:http://blog.csdn.net/lnho2015/article/details/50962989 以下是我个人做题过程中的一些体会: 1. LeetCode的题库越来越大,截止到目 ...
- lintcode 刷题 by python 部分链表题总结(2)
本篇博客对最近做的链表的算法题做个简单的小结,主要描述题目和提供解题思路,具体代码见我的 github:https://github.com/MUSK1881/lintcode-by-python 3 ...
- BZOJ刷题指南(转)
基础(65) 巨水无比(4):1214.3816:2B题:1000A+B:2462:输出10个1 模拟/枚举/暴力(15):4063傻子模拟:1968小学生暴力:1218前缀和暴力:3856读英文:4 ...
- lintcode刷题笔记(一)
最近开始刷lintcode,记录下自己的答案,数字即为lintcode题目号,语言为python3,坚持日拱一卒吧... (一). 回文字符窜问题(Palindrome problem) 627. L ...
- LintCode刷题笔记-- LongestCommonSquence
标签:动态规划 题目描述: Given two strings, find the longest common subsequence (LCS). Your code should return ...
随机推荐
- python学习笔记(八)python操作Excel
一.python操作excel,python操作excel使用xlrd.xlwt和xlutils模块,xlrd模块是读取excel的,xlwt模块是写excel的,xlutils是用来修改excel的 ...
- 脱离JVM? Hadoop生态圈的挣扎与演化
本文由知乎<大数据应用与实践>专栏 李呈祥授权发布,版权所有归作者,转载请联系作者! 新世纪以来,互联网及个人终端的普及,传统行业的信息化及物联网的发展等产业变化产生了大量的数据,远远超出 ...
- HTML5中Video和Audio
相关属性 src属性 该属性指定媒体数据的URL地址. autoplay属性 在该属性中指定是否在页面加载后自动播放,使用方法: <video src="test.mov" ...
- python 中字典的操作(增、删、改、查)
字典是另一种可变容器模型,且可存储任意类型对象,下标从0开始,最后一个为-1. 字典的每个键值(key=>value)对用冒号(:)分割,每个对之间用逗号(,)分割,整个字典包括在花括号({}) ...
- python中的内置函数总结
官方文档 一. 数学函数 #abs() 绝对值 #bin() 二进制 0b #oct() 八进制 0o #hex() 十六进制 0x #complex 复数 x=1-2j print(x) print ...
- Extjs添加行双击事件
var grid = new Ext.grid.GridPanel({ store: store, trackMouseOver: false, disableSelection: true, aut ...
- Linux系统——date命令
date命令 作用:用来显示或设定系统的日期与时间. 参数 -d<字符串>:显示字符串所指的日期与时间.字符串前后必须加上双引号: -s<字符串>:根据字符串来设置日期与时间. ...
- hbase(二)
一.HBase简介 1.1简介 hbase是bigtable的开源山寨版本.是建立的hdfs之上,提供高可靠性.高性能.列存储.可伸缩.实时读写的数据库系统.它介于nosql和RDBMS之间,仅能通过 ...
- URAL - 1091 Tmutarakan Exams (简单容斥原理)
题意:K个不同数组成的集合,每个数都不超过S且它们的gcd>1.求这样的数的个数 分析:从2开始枚举gcd,但这样会发生重复.譬如,枚举gcd=2的集合个数和gcd=3的集合个数,枚举6的时候就 ...
- [转]loadrunner:系统的平均并发用户数和并发数峰值如何估算
一.经典公式1: 一般来说,利用以下经验公式进行估算系统的平均并发用户数和峰值数据 1)平均并发用户数为 C = nL/T 2)并发用户数峰值 C‘ = C + 3*根号C C是平均并发用户数,n是l ...