LeetCode.jpg
1. 1
2. 11
3. 21
4. 1211
5. 111221
1 被读作 "one 1" ("一个一") , 即 11。
11 被读作 "two 1s" ("两个一"), 即 21。
21 被读作 "one 2", "one 1" ("一个二" , "一个一") , 即 1211。
给定一个正整数 n ,输出报数序列的第 n 项。
注意:整数顺序将表示为一个字符串。
案例1:
输入: 1
输出: "1"
案例2:
输入: 4
输出: "1211"
外层循环正整数n,内层循环获取到的字符串,比较前一位和后一位,相同则增加count,然后再拼接字符串
func countAndSay(_ n: Int) -> String {
var say = "1"
for _ in 1..<n {
var cnt = 1
var tempSay = ""
for j in 0..<say.count {
if (say.substingInRange(j..<j+1) == say.substingInRange(j+1..<j+2)) {
cnt += 1
} else {
tempSay += String(cnt) + String(say.substingInRange(j..<j+1)!)
cnt = 1
}
}
say = tempSay
}
return say
}
extension String {
//获取子字符串
func substingInRange(_ r: Range<Int>) -> String? {
if r.lowerBound < 0 || r.upperBound > self.count {
return nil
}
let startIndex = self.index(self.startIndex, offsetBy:r.lowerBound)
let endIndex = self.index(self.startIndex, offsetBy:r.upperBound)
return String(self[startIndex..<endIndex])
}
}
Swift中取范围内字符子串参考:Swift4 获取String子字符串这里直接把代码拷过来了
思想和方法一是一致的,但明显取下标方便,然后数组效率比字符串要高
代码二:
func countAndSay(_ n: Int) -> String {
var say = "1"
if n == 1 {
return say
}
for _ in 1..<n {
var tempSay = ""
var cnt = 1
var chars = Array(say)
for j in 0..<say.count {
//条件太长还是括起来比较好
if (j + 1 < chars.count && chars[j] == chars[j + 1]) {
cnt += 1
} else {
tempSay.append("\(cnt)")
tempSay.append(chars[j])
cnt = 1
}
}
say = tempSay
}
return say
}
就减少了一次循环、、、
func countAndSay2(_ n: Int) -> String {
var say = "1"
if n == 1 {
return say
}
for _ in 1..<n {
var tempSay = ""
var cnt = 1
var chars = Array(say)
var current = chars[0]
for j in 1..<say.count {
if chars[j] == current {
cnt += 1
} else {
tempSay.append("\(cnt)")
tempSay.append(current)
cnt = 1
current = chars[j]
}
}
tempSay.append("\(cnt)")
tempSay.append(current)
say = tempSay
}
return say
}
结果又快了那么一点点、、、没啥影响、、