php fizz,php面试题:FizzBuzz最短连续序列问题

[php]代码库<?php

/**

* FizzBuzz问题:

*

* The aim of the test is to discover the shortest sequence of consecutive numbers, which when they are run through the fizzbuzz algorithm produce the required output.

*

* For example, the shortest sequence that produces fizz is 3

*

* When looking for the shortest sequence for

*

* fizz buzz

*

* one sequence that produces that output is

*

* 3, 4, 5

*

* However, this isn't the shortest. The shortest sequence is 9, 10

*

* In our case, we are only interested in the numbers between 1 and 100, so be sure you limit your calculations to that range, otherwise you are likely to exceed timeout limits.

*

* InverseFizzBuzz

*

* @author 剑锋

* @qq 1421560459

*

*/

class InverseFizzBuzz {

private $list;

private $max = 100; //扫描最大值

public function __construct($list) {

$this->list = $list;

}

/**

* 查找序列

* 思路:遍历1-max,分别遍历字符数组,找到fizz或buzz,放到散列结果中保存;补全散列结果得到连续结果序列;找到结果长度最短的

* Enter description here ...

*/

public function sequence() {

$resultList = array(); //结果集

//遍历1-max

for($i = 1; $i <= $this->max; $i++){

$resultHash = array(); //结果散列

$result = array(); //结果序列之一

$last = $i; //上一个扫描结果

$isFull = true; //标记是否找到完整序列

//查找fizz或buzz

foreach($this->list as $k => $v){

$index = $i; //索引

switch($v){

case 'fizz':{

$index = $this->_scanNextFizz($last);

if ($index){ //找到fizz

array_push($resultHash, $index);

$last = $index;

}else{ //未找到fizz

$isFull = false;

$last++;

}

break;

}

case 'buzz':{

$index = $this->_scanNextBuzz($last);

if ($index){ //找到buzz

array_push($resultHash, $index);

$last = $index;

}else{ //未找到buzz

$isFull = false;

$last++;

}

break;

}

default:{

break;

}

}

}

//填充数字间隔,不完整序列不填充

if ($resultHash && $isFull){

$time = count($resultHash) - 1; //循环终止下标

for($j = $resultHash[0]; $j <= $resultHash[$time]; $j++){

array_push($result, $j);

}

array_push($resultList, $result);

}

}

//判断是否存在结果(例如 buzz fizz buzz)

if (count($resultList) == 0){

return null;

}

//查找最短结果

$count = $this->max;

foreach ($resultList as $v){

$length = count($v);

if ($length < $count){

$count = $length;

$result = $v;

}

}

return $result;

}

/**

* 查找下一个Fizz

*

* Enter description here ...

* @param unknown_type $current

*/

private function _scanNextFizz($current){

for($i = $current + 1; $i <= $this->max; $i++){

if($i % 5 == 0){ //上次结果与今次结果之间不能有buzz

return 0;

}

if($i % 3 == 0){

return $i;

}

}

return 0;

}

/**

* 查找下一个Buzz

*

* Enter description here ...

* @param unknown_type $current

*/

private function _scanNextBuzz($current){

for($i = $current + 1; $i <= $this->max; $i++){

if($i % 3 == 0){ //上次结果与今次结果之间不能有fizz

return 0;

}

if($i % 5 == 0){

return $i;

}

}

return 0;

}

}

//测试

$inverse = new InverseFizzBuzz(array('fizz', 'buzz', 'fizz')); //3 4 5 6

var_dump($inverse->sequence());

?>

694748ed64b9390909c0d88230893790.png

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值