PHP算法02
PHP算法02
PHP算法02

01). 输出 1 到 100 之间的素数(质数)

用一个数分别去除2到这个数之间的所有数,如果被整除就是素数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
// 2 3 5 7 11 13 17 19 23 29 31 37 41 43 47 53 59 61 67 71 73 79 83 89 97 
//分析: 用一个数分别去除2到这个数之间的所有数,如果被整除就是素数
for ($i = 1; $i <= 100; $i++) {
$k = 0;
//判断开始和结束的值是否也是素数
for ($j = 1; $j <= $i; $j++) {
if ($i % $j == 0) {
$k++;
}
}
if ($k == 2) {
echo $i;
echo "&nbsp;&nbsp;";
}
}

02). 打印出所有的 “水仙花数 “

1
2
3
4
5
6
7
8
9
10
11
12
13
14
// 打印出所有的 "水仙花数 ", 三位的水仙花数共有4个:153,370,371,407
// 所谓 "水仙花数 "是指一个三位数,其各位数字立方和等于该数本身。
// 例如:153是一个 "水仙花数 ",因为 1^3 + 5^3+ 3^3 = 153

for ($i = 100; $i < 1000; $i++) {
$hunderds = floor($i / 100);
$tens = floor($i / 10) % 10;
$ones = floor($i % 10);
$temp = pow($hunderds, 3) + pow($tens, 3) + pow($ones, 3);
if ($temp == $i) {
echo $i;
echo "&nbsp;";
}
}

03). 正整数分解质因数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
// 将一个正整数分解质因数。例如:输入90,打印出90=2*3*3*5。
// 分析:
// 对n进行分解质因数,应先找到一个最小的质数k,然后按下述步骤完成:
// (1)如果这个质数恰等于n,则说明分解质因数的过程已经结束,打印出即可。
// (2)如果n<>k,但n能被k整除,则应打印出k的值,并用n除以k的商,作为新的正整数n,重复执行第一步。
// (3)如果n不能被k整除,则用k+1作为k的值,重复执行第一步

$n = 90;
echo $n . '=';
for ($i = 2; $i < $n + 1; $i ++){
while ($n % $i == 0 && $n != $i) {
$n /= $i;
echo $i . "*";
}
if ($n == $i) {
echo $i;
break;
}
}

04). 三目条件嵌套

1
2
3
4
5
6
7
8
9
10
// 利用条件运算符的嵌套来完成此题:
// 学习成绩> =90分的同学用A表示,
// 60-89分之间的用B表示,
// 60分以下的用C表示。

$score = 89;

$grade = $score >= 90 ? 'A' : ($score >= 60 && $score <= 89 ? 'B' : "C");

echo $grade;

05). 输入两个正整数m和n,求其最大公约数和最小公倍数

最大公约数 =(A×B)/ 最小公倍数; 公式:由于两个数的乘积等于这两个数的最大公约数与最小公倍数的积。

辗转相除法, 又名欧几里德算法,是求最大公约数的一种方法。以除数和余数反复做除法运算,最终当余数为 0 时,取当前算式除数为 最大公约数。算法举例:

1
2
3
4
5
6
7
8
9
10
11
12
// demo1; 有两个数字[1997,615]
// 1997 % 615 = 152 (余 152)
// 615 % 152 = 7 (余7)
// 152 % 7 = 5 (余5)
// 7 % 5 = 2 (余2)
// 5 % 2 = 1 (余1)
// 2 % 1 = 0 (余0) 这个除数1就是最大公约数

// demo2; 有两个数字[16,6]
// 16 % 6 = 4; (余数4)
// 6 % 4 = 2; (余数2)
// 4 % 2 = 0; (余数2) 这个除数2就是最大公约数
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
// 题目:输入两个正整数m和n,求其最大公约数和最小公倍数

// 在循环中,只要除数不等于0,用较大数除以较小的数,
// 将小的一个数作为下一轮循环的大数,取得的余数作为下一轮循环的较小的数,
// 如此循环直到较小的数的值为0,
// 返回较大的数,此数即为最大公约数,最小公倍数为两数之积除以最大公约数。

// 这种方法叫做: 辗除法
function f($x, $y)
{
if ($x < $y) {
$temp = $x;
$x = $y;
$y = $temp;
}
while ($y!=0) {
if ($x==$y){
return $x;
}else{
$k = $x % $y;
$x = $y;
$y = $k;
};
}
return $x;
}
$a = 21; $b = 24;
$m = f($a, $b); //最大公约数
$n = $a * $b / $m; //最小公倍数
echo '最大公约数为: ' . $m."&nbsp;&nbsp;";
echo '最小公倍数为: ' . $n."&nbsp;&nbsp;";

//------------------------------------------------------------
// 方法2, 使用php自带的函数,获取最小公约数
$gcd = gmp_gcd("21", "24");
echo gmp_strval($gcd) . "\n";

06) 求s=a+aa+aaa+aaaa+aa…a的值

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
// 题目:求s=a+aa+aaa+aaaa+aa...a的值,其中a是一个数字。
// 例如2+22+222+2222+22222(此时共有5个数相加),几个数相加有键盘控制

//$num 数字 $count 几个数相加
function fun($num, $count)
{
$temp = 0;
$sum = 0;
for ($i = 0; $i < $count; $i++) {
$temp = $temp + $num; //获取需要相加的数字
$sum = $sum + $temp; //数字相加
$num = $num * 10;
}
return $sum;
}

// echo fun(2, 2); //2+22=24
// echo fun(2, 3); //2+22+222=246
// echo fun(2, 4); //2+22+222+2222=2468
echo fun(2, 5); //2+22+222+2222+22222=24690

07) 完数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
// 题目:一个数如果恰好等于它的因子之和,这个数就称为 "完数 "。
// 例如6=1+2+3.编程 找出1000以内的所有完数
function fun()
{
echo "1到1000的完数有: ";
for ($i = 1; $i < 1000; $i++) {
$t = 0;
for ($j = 1; $j <= $i / 2; $j++) {//$i/2 减少循环次数 for ($j = 1; $j < $i ; $j++) {
if ($i % $j == 0) {
$t = $t + $j;
}
}
if ($t == $i) {
echo($i ." ");
}
}
}

fun(); //1到1000的完数有: 6 28 496

08) 四个数字组成三位数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
// 题目:有1、2、3、4四个数字,
// 能组成多少个互不相同且无重复数字的三位数 都是多少
function fun()
{
$x = 0;
$y = 0;
$z = 0;
$arr = [];
$_count = 0; //统计个数

for ($x = 1; $x < 5; $x++) {
for ($y = 1; $y < 5; $y++) {
for ($z = 1; $z < 5; $z++) {
if ($x != $y && $y != $z && $x != $z) {
$_count++;
// echo $x * 100 + $y * 10 + $z.'<br/>';
array_push($arr, $x * 100 + $y * 10 + $z);
}
}
}
}
array_push($arr, ['count' => $_count]);
return $arr;
}

print_r(fun());

09) 某年某月某日,第几天

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
// 输入某年某月某日,判断这一天是这一年的第几天
function fun($year,$month,$day)
{
switch ($month) {
case 1:$sum=0;break;
case 2:$sum=31;break;
case 3:$sum=59;break;
case 4:$sum=90;break;
case 5:$sum=120;break;
case 6:$sum=151;break;
case 7:$sum=181;break;
case 8:$sum=212;break;
case 9:$sum=243;break;
case 10:$sum=273;break;
case 11:$sum=304;break;
case 12:$sum=334;break;
default:printf("data error");break;
}
$sum = $sum + $day;
if ($year % 400 == 0 || ($year % 4 == 0 && $year % 100 != 0)) { //判断是不是闰年
$leap = 1;
} else {
$leap = 0;
}
if ($leap == 1 && $month > 2) { //如果是闰年切月份大于2,总天数应该加一天
$sum++;
}
return $sum;
}

print_r(fun(2019, 03, 1));

10) 三元运算符及比较3个数的大小,输出最大的数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
// 三元运算符及比较3个数的大小,输出最大的数
function fun($a,$b,$c)
{
$d= $a > $b ? ($a > $c ? $a : $c) : ($b > $c ? $b : $c);
return $d;
}

echo fun(1, 2, 3);

//-----------------------------------
// 比较3个数的大小, 并从小到大输出
function fun($i, $j, $k)
{
$x = 0;
if ($i > $j) {
$x = $i;
$i = $j;
$j = $x;
}
if ($i > $k) {
$x = $i;
$i = $k;
$k = $x;
}
if ($j > $k) {
$x = $j;
$j = $k;
$k = $x;
}
return $i . " " . $j . " " . $k;
}

echo fun(10, 0, 3);