[LeetCode] Split Array into Fibonacci Sequence 分割数组成斐波那契序列
Given a string S
of digits, such as S = "123456579"
, we can split it into a Fibonacci-like sequence [123, 456, 579].
Formally, a Fibonacci-like sequence is a list F
of non-negative integers such that:
0 <= F[i] <= 2^31 - 1
, (that is, each integer fits a 32-bit signed integer type);F.length >= 3
;- and
F[i] + F[i+1] = F[i+2]
for all0 <= i < F.length - 2
.
Also, note that when splitting the string into pieces, each piece must not have extra leading zeroes, except if the piece is the number 0 itself.
Return any Fibonacci-like sequence split from S
, or return []
if it cannot be done.
Example 1:
Input: "123456579"
Output: [123,456,579]
Example 2:
Input: "11235813"
Output: [1,1,2,3,5,8,13]
Example 3:
Input: "112358130"
Output: []
Explanation: The task is impossible.
Example 4:
Input: "0123"
Output: []
Explanation: Leading zeroes are not allowed, so "01", "2", "3" is not valid.
Example 5:
Input: "1101111"
Output: [110, 1, 111]
Explanation: The output [11, 0, 11, 11] would also be accepted.
Note:
1 <= S.length <= 200
S
contains only digits.
这道题给了我们一个字符串,让我们分割成斐波那契序列,至少要分成三个数,并且满足斐波那契数列的性质。关于其性质,博主有个口诀可以快速记忆,那就是大学食堂里今天的汤是昨天的汤加上前天的汤。题目中给的例子挺多的,便于理解题意,其中例子4还强调了不能有leading zeros。但是关于overflow的test case却只字未提,害的博主fail了N多次,才最终handle了所有的溢出的错误。由例子5我们可以看出,符合题意的数列其实可能不止一种,但是本题就让返回一个就行了。不管返回几个,总之不是求极值,DP在这里就不好使了,只能用递归了,由于不知道如何分割,所以肯定需要遍历所有的情况。我们用一个数组out来记录已经组成的序列,用结果res来保存结果。当out数组的个数大于等于3,并且已经遍历完了字符串S,那么此时就是可以把out数组中的内存赋值给结果res了,那么之后只要检测结果res不为空时,直接返回就可以了,这是个很好的剪枝操作,因为此题只需要一个正确答案即可(返回所有情况将作为follow up在本文的底部讨论)。
现在来考虑递归函数的主体该怎么写,既然不知道要如何分割,那么就要尝试所有的情况,一个数字,两个数字,一直到末尾,那么就可以遍历字符串S,然后取子串即可。但从什么位置开始呢,每次都从头吗,这道题都数字不能重复使用,所以应该用个变量start来记录当前遍历到的位置,那么我们从start位置起,每次取 i-start+1 长度的子串 cur,此时在转为int之前,需要先处理leading zeros的情况,判断若cur长度大于1,且首字符为0,直接break,还就是若cur的长度大于10,也break,为啥呢?因为整型的最大值是 2147483647,只有10位,所以当cur长度大于10时,一定会溢出。当cur长度为10时,也有可能溢出,这个在之后处理。好,现在将cur转为长整型 long,因为长度为10也可能溢出,所以要先转为长整型,然后在判断若大于整型最大值 INT_MAX,直接break。接下来就要考虑是否要加入out数组了,当out数字的个数不到2个的时候,我们可以直接加入当前数字,若大于等于2个,需要考虑是否满足斐波纳切数列的性质,即当前数字是否等于前两个数字之和,满足的话才加入,不然就跳过,注意这里不能直接break,因为之后的数字也许可能满足要求。加入out数组之后,就可以调用递归了,此时起始位置传入 i+1,之后再恢复out的状态即可,参见代码如下:
class Solution {
public:
vector<int> splitIntoFibonacci(string S) {
vector<int> res, out;
helper(S, , out, res);
return res;
}
void helper(string& S, int start, vector<int>& out, vector<int>& res) {
if (!res.empty()) return;
if (start >= S.size() && out.size() >= ) {
res = out; return;
}
for (int i = start; i < S.size(); ++i) {
string cur = S.substr(start, i - start + );
if ((cur.size() > && cur[] == '') || cur.size() > ) break;
long num = stol(cur), len = out.size();
if (num > INT_MAX) break;
if (out.size() >= && num != (long)out[len - ] + out[len - ]) continue;
out.push_back(num);
helper(S, i + , out, res);
out.pop_back();
}
}
};
讨论:这道题只让我们返回了一个斐波那契数列,一个很好的follow up就是返回所有满足题意的序列,就像例子5一样,把两种符合题意的组合都返回出来。其实改起来相当的容易,只需要将结果res换成一个二维数组来保存所有的情况,然后在递归函数中,首先判断如果已经遍历到了S的末尾,并且out数组中的个数大于等于3了,那么将out数组加入结果res即可,其余部分和上面的解法并没有啥区别,代码参见评论区一楼。
类似题目:
参考资料:
https://leetcode.com/problems/split-array-into-fibonacci-sequence/
LeetCode All in One 题目讲解汇总(持续更新中...)
[LeetCode] Split Array into Fibonacci Sequence 分割数组成斐波那契序列的更多相关文章
- [LeetCode] Split Array With Same Average 分割数组成相同平均值的小数组
In a given integer array A, we must move every element of A to either list B or list C. (B and C ini ...
- [LeetCode] Split Array with Equal Sum 分割数组成和相同的子数组
Given an array with n integers, you need to find if there are triplets (i, j, k) which satisfies fol ...
- [LeetCode] Length of Longest Fibonacci Subsequence 最长的斐波那契序列长度
A sequence X_1, X_2, ..., X_n is fibonacci-like if: n >= 3 X_i + X_{i+1} = X_{i+2} for all i + 2 ...
- [Swift]LeetCode842. 将数组拆分成斐波那契序列 | Split Array into Fibonacci Sequence
Given a string S of digits, such as S = "123456579", we can split it into a Fibonacci-like ...
- [LeetCode] 548. Split Array with Equal Sum 分割数组成和相同的子数组
Given an array with n integers, you need to find if there are triplets (i, j, k) which satisfies fol ...
- 剑指offer二刷——数组专题——斐波那契数列
题目描述 大家都知道斐波那契数列,现在要求输入一个整数n,请你输出斐波那契数列的第n项(从0开始,第0项为0,第1项是1). n<=39 我的想法 斐波那契数列定义:F(0)=0,F(1)=1, ...
- 冒泡排序 and 选择排序 变量打印斐波拉契数列 and 数组打印斐波拉契数列
1 排序 1.1 冒泡排序 #include <stdio.h> int main() { ]; printf("input six int numbers:\n"); ...
- LeetCode 842. Split Array into Fibonacci Sequence
原题链接在这里:https://leetcode.com/problems/split-array-into-fibonacci-sequence/ 题目: Given a string S of d ...
- [LeetCode] Split Array into Consecutive Subsequences 将数组分割成连续子序列
You are given an integer array sorted in ascending order (may contain duplicates), you need to split ...
随机推荐
- PMI-ACP练习题知识积累-打印版
敏捷铁三角的参数:价值,质量,约束.传统的铁三角包括的参数是范围,进度和成本 敏捷计划的三个主要层级为:发布计划,迭代计划,每日计划 敏捷开发模型的特征包括 开发由多个迭代组成. 敏捷拥抱不确定性,而 ...
- vs2013、vs2015使用.net4.5框架智能提示英文转成中文
安装完VS2013.VS2015使用.net framework 4.5框架时,代码补全中智能提示信息全是英文解决方案:关闭VS2013.VS2015:将zh-Hans 目录替换以下目录 C:\Pro ...
- 使用freemarker生成word文档处理表格数据
1.把需要从数据库取值的字段用${}括起来,如:${busDate};2.表格数据的循环需要加标签:<#list tbl3 as tbl3>......</#list>< ...
- jqGrid基础写法
$("#jqGrid").jqGrid({ url: baseURL + 'sys/scheduleLog/list', datatype: "json", c ...
- MySQL Percona server 5.5 安装审计插件
近期,公司要求对MySQL 数据库上操作进行审计:通过了解MySQL 官方企业版(付费版)本中集成了audit_log审计插件,但是社区开源版本中并不包含该插件,也没提供下载.进一步了解 MariaD ...
- luoguP1131
时态同步 ...这道题我也不知道咋\(A\)的. 思路: \(anst\) 距离 \(s\) 的最长距离,\(ansp\) 某一节点到祖先所有边的权值和这些些加过的权值和 先求出到\(s\)距离最长的 ...
- Python之MySQL库表操作
一:库操作 1.1 增 # 语法 # create database 库名 default charset utf8; create database db1 default charset utf8 ...
- 自定义Section
转载 :http://www.cnblogs.com/gaobing/p/6047746.html <configSections> 元素必须是 configuration 元素的第一个子 ...
- Bean拷贝
相当于C#的AutoMapper public class CloneUtils { /** * 拷贝对象 * @param source * @param classType * @return * ...
- thinkPHP实现APP微信支付
控制器 class Pay extends Controller { const WX_PAY_URL = "https://api.mch.weixin.qq.com/pay/unifie ...