问题描述

FizzBuzz问题:一个大于0的自然数能整除3,将输出“Fizz”;能整除5,将输出“Buzz”;能整除3和5,将输出“FizzBuzz”;否则输出自己。

逆FizzBuzz问题最短序列:已知一个FizzBuzz问题的非数字输出序列,求能获得该序列的最短连续数字序列。如“Fizz”的最短序列是“3”,“Fizz Buzz”的最短序列是“9 10”,而不是“3 4 5”。

编程实现

 <?php

 /**
* @author cenze
*
* 反FizzBuzz问题求最短序列
*
* $inverseFizzBuzz = new InverseFizzBuzz([
* 'fizz',
* 'fizz',
* 'buzz',
* ]);
* $inverseFizzBuzz->sequence():
* Array ( [0] => 6 [1] => 7 [2] => 8 [3] => 9 [4] => 10 )
*/
class InverseFizzBuzz
{
// FizzBuzz问题赋值
const FizzBuzz = [
'fizz' => 3,
'buzz' => 5,
'fizzbuzz' => 15
]; // 预定义问题区间
private $range = [
1,
100
]; // 待求序列
private $list = []; // 待求序列包含项数统计
private $listItemsCount = 0; public function __construct($list = [], $range = [])
{
$this->init($list, $range);
} /**
* 待求序列、区间初始化
*
* @param array $list
* 待求序列
* @param array $range
* 问题区间
* @param bool $check
* 是否检查属性已完成初始化
*
* @return void
*/
private function init($list = [], $range = [], $check = false)
{
if ($list) {
$this->list = $this->inverseList($list);
$this->listItemsCount = count($this->list);
if (! $this->listItemsCount) {
exit('Invalid list.');
}
} if ($range) {
$this->range = $range;
} if ($check) {
if (! $this->list) {
exit('Property list uninitialized.');
}
}
} /**
* 将待求解序列反转
*
* @param array $list
* 待求解序列
*
* @return mixed
*/
private function inverseList($list)
{
$inverseList = [];
foreach ($list as $item) {
if (! array_key_exists($item, self::FizzBuzz)) {
return null;
}
$inverseList[] = self::FizzBuzz[
$item
];
} return $inverseList;
} /**
* 搜索最短序列是否存在
*
* @param array $list
* 待求序列
* @param array $range
* 问题区间
*
*
* @return mixed
*/
public function sequence($list = [], $range = [])
{
$this->init($list, $range, true); $sequences = $this->findSequences();
if (! $sequences) {
return 'Found no sequences.';
} $sequence = $this->findShortestSequence($sequences);
// 将最短序列序列化后返回
return range($sequence[0], $sequence[$this->listItemsCount - 1]);
} /**
* 搜索最短序列(未序列化)
*
* @param array $sequences
* 序列集合,包含最短序列
*
* @return array
*/
private function findShortestSequence($sequences)
{
// 默认第一条为最短
$shortestSequence = $sequences[0];
// 把每一个序列看做一条路径,都有对应的长度。记录最短的序列长度
$shortestSequenceLength = $sequences[0][$this->listItemsCount - 1] - $sequences[0][0];
// 为array_reduce()定义一个callback,用来搜索最短序列
$findShortestSequence = function ($shortestSequence, $currentSequence) use(&$shortestSequenceLength) {
$currentSequenceLength = $currentSequence[$this->listItemsCount - 1] - $currentSequence[0];
if ($currentSequenceLength < $shortestSequenceLength) {
$shortestSequenceLength = $currentSequenceLength;
return $currentSequence;
} else {
return $shortestSequence;
}
}; return array_reduce($sequences, $findShortestSequence, $shortestSequence);
} /**
* 从指定位置开始搜索指定项目的序列
*
* @param int $item
* 指定项目
* @param int $start
* 起始搜索位置
*
* @return int
*/
private function findItemSequenceFromPosition($item, $start)
{
if ($start % $item == 0) {
return $start;
} return $start + ($item - $start % $item);
} /**
* 从指定位置开始搜索首个序列
*
* @param int $start
* 起始搜索位置
*
* @return mixed
*/
private function findSequenceFromPosition($start)
{
$listSequence = [];
for ($i = 0; $i < $this->listItemsCount; $i ++) {
$itemSequence = $this->findItemSequenceFromPosition($this->list[$i], $start);
if ($itemSequence > $this->range[1]) {
return null;
} else {
$listSequence[] = $itemSequence;
$start = $itemSequence + 1;
}
} return $listSequence;
} /**
* 找到多个序列,其中包括最短序列
*
* @return void
*/
private function findSequences()
{
$sequences = [];
// 以第一个项为初始搜索位置在预定区间中搜索,且以第一个项为递增步长向后逐步搜索
for ($start = $this->list[0]; $start <= $this->range[1]; $start += $this->list[0]) {
// 只需找到指定位置开始的第一个序列即可
if ($sequence = $this->findSequenceFromPosition($start)) {
$sequences[] = $sequence;
}
} return $sequences;
}
}

逆FizzBuzz问题求最短序列的更多相关文章

  1. hdu 1394 zoj 1484 求旋转序列的逆序数(并归排序)

    题意:给出一序列,你可以循环移动它(就是把后面的一段移动到前面),问可以移动的并产生的最小逆序数. 求逆序可以用并归排序,复杂度为O(nlogn),但是如果每移动一次就求一次的话肯定会超时,网上题解都 ...

  2. hdu 1394 Minimum Inversion Number (裸树状数组 求逆序数 && 归并排序求逆序数)

    题目链接 题意: 给一个n个数的序列a1, a2, ..., an ,这些数的范围是0-n-1, 可以把前面m个数移动到后面去,形成新序列:a1, a2, ..., an-1, an (where m ...

  3. 动态规划求一个序列的最长回文子序列(Longest Palindromic Substring )

    1.问题描述 给定一个字符串(序列),求该序列的最长的回文子序列. 2.分析 需要理解的几个概念: ---回文 ---子序列 ---子串 http://www.cnblogs.com/LCCRNblo ...

  4. [zz]求一维序列的信息熵(香浓熵)的matlab程序实例

    对于一个二维信号,比如灰度图像,灰度值的范围是0-255,因此只要根据像素灰度值(0-255)出现的概率,就可以计算出信息熵.    但是,对于一个一维信号,比如说心电信号,数据值的范围并不是确定的, ...

  5. poj 2001:Shortest Prefixes(字典树,经典题,求最短唯一前缀)

    Shortest Prefixes Time Limit: 1000MS   Memory Limit: 30000K Total Submissions: 12731   Accepted: 544 ...

  6. 39. 求分数序列前N项和

    求分数序列前N项和 #include <stdio.h> int main() { int i, n; double numerator, denominator, item, sum, ...

  7. 20. 求阶乘序列前N项和

    求阶乘序列前N项和 #include <stdio.h> double fact(int n); int main() { int i, n; double item, sum; whil ...

  8. 19. 求平方根序列前N项和

    求平方根序列前N项和 #include <stdio.h> #include <math.h> int main() { int i, n; double item, sum; ...

  9. OpenJudge计算概论-求分数序列和

    /*======================================================================== 求分数序列和 总时间限制: 1000ms 内存限制 ...

随机推荐

  1. jqGrid 常用 总结 -1

    这篇文章是因为,我们在做的后台项目,里面有大量的表格统计,这个不可能自己手写,所以其中的表格使用的是jqgrid. 这个插件其实使用起来还是不错的,里面有很多的功能很赞.这篇博客就是自己的的一个记录, ...

  2. Deepin Linux系统的日常使用总结(日常施工)

    1.登录root权限用户 sudo su 2.安装软件语句 apt-get install <package_name> 相对的, 安装:apt-get install <packa ...

  3. 模板引擎artTemplate的使用

    1.引入template文件 <script src = js/template-native.js></script> 2.写模板 <script type=" ...

  4. vue 日期时间过滤器

    来自:https://blog.csdn.net/m0_37068028/article/details/72898154 侵删 来自:https://segmentfault.com/a/11900 ...

  5. 27号华为笔试(三道ac两道)

    三道题目case:100,100,0: 三个题目: 前两个都全部ac了,第三题没时间: 记录一下大概的思路: 第一题 主要通过Java中的字符串处理函数:然后控制字符串输入格式: 卡bug的点: 1: ...

  6. 解决laravel Class 'Doctrine\DBAL\Driver\PDOMySql\Driver' not found 错误

    这个错误的原因来自于没有安装一个依赖库: 官方文档说明如下: Modifying Columns Prerequisites Before modifying a column, be sure to ...

  7. win10怎么进入和退出安全模式?

    在Win10系统里同时按下”Win+R“组合按键,在打开的运行对话框里输入命令:msconfig,然后点击确定,如下图所示. 点击打开系统配置窗口,选择引导选项卡,如下图所示. 在引导选项卡窗口下,将 ...

  8. Java基础系列--03_Java中的方法描述

    方法 (1)方法的定义:就是完成特定功能的代码块. 注意:在很多语言里面有函数的定义,而在Java中,函数被称为方法. (2)格式: 修饰符 返回值类型 方法名(参数类型 参数名1,参数类型 参数名2 ...

  9. 消息队列比较-rabbitmq/kafka/rocketmq/ONS

    主要是比较这几种队列中间件: rabbitmq kafka rocketmq ONS 分以下几个维度来比较 高并发 毫无疑问KAFKA发消息的速度是最快的 ROCKETMQ/ONS次之 rabbitm ...

  10. MongoDB系列:四、spring整合mongodb,带用户验证

    在前面的两篇博客 MongoDB常用操作练习.springboot整合mongoDB的简单demo中,我们基本上熟悉了mongodb,也把它与spring boot进行了整合并且简单使用.在本篇博客中 ...