考基本功的 10 个简单编程题

来源:互联网 发布:看外汇的软件 编辑:程序博客网 时间:2024/06/08 20:10

一、给一个数 N,判定这个数是否是素数。
1、先让面试者说素数的定义,如果不知道可以提示素数的定义
2、最差的面试者,会没有思路,这是很可怕的,大学第一学期学完,应该学会这个题
3、一般的面试者,能比较费劲地写出正确的程序,但是可能存在边界、标记等问题。
4、写出程序出来,可以进一步问,优化的空间,在哪里,所谓优化,无非就是时间和空间复杂度。
5、只有少数的面试者,能进行几轮优化
6、有训练的面试者可能知道一些特定的高效方法

<?php
    check_ss(8);
 
    function check_ss($num) {
        for($i=2; $i < $num ; $i++) {
            if($num % $i == 0) {
                echo $num. '不是素数';
                exit;
            }
        }
        
        echo $num. '是素数';
    }

二、给一个数 N,把 2 到 N 之间的素数输出出来
1、这个题比上面这个难度加大了一层
2、可以限定,不让其使用子函数,增加逻辑上的复杂度
3、其他的,同样一层层考优化的方法

<?php
 
$no=0;//用于标记经检验前后是否是素数,0表示是;1不是;
 
for($i=2;$i<=1000;$i++){//循环2-1000
 
    for($j=2;$j<$i;$j++){//检验当前$i是否是素数
        if($i%$j==0){
            $no=1;//如果取余得0,不是素数,改值为1
        }
    }
 
if($no==0){echo $i;}//经过检验后如果$no仍为0,则$i是素数。
 
}
?>

三、写出三角状的 9*9 乘法表
1、这个题目面向基础比较差的面试者
2、最差的面试者,也会说没有思路,在学校会写,现在忘记了
3、比较一般的能写出来,更进行一步的,可以让其用几种循环来写,写倒三角
4、如果都没有问题,循环思维逻辑值得肯定
<?php

    for($a = 1; $a <10; $a++){
        echo "<table>";
        echo "<tr>";
        for ($b=1; $b <= $a; $b++) {
            echo "<td>";
            echo "$a*$b=".$a*$b;
            echo "</td>";
        }
        echo "</tr>";
        echo "</table>";
    }
?>

四、用递归编写求和或者求阶乘的函数
1、可以先让其不用递归写一遍
2、再让其递归实现
3、最差的面试者同样无法下手
4、接下来可以探讨递归的一些优劣之处,在哪些常见算法中用到了递归
5、也可以问问1024的阶乘有多少个零这种的问题。

php递归的方法求和1+2+3+...+n
function add($n){
  if($n==1) return 1;
else
   return $n+add($n-1);   //没注意
}

用php实现1+(1+2)+(1+2+3)+...+(1+2+...n) 递归求和
function getSum($n) {
  if ($n > 1) {
    $tempSum = $n * (1 + $n) / 2;  // 当然这部分可以拆成另一个递归来求和,如果有需要在说
    return $tempSum + getSum(--$n);
  }
  else {
    return $n;
  }
}
$result = getSum(20);

求n的阶乘
<?php

function f($n) 

   $out = -1;
   if($n<0)
       echo "输入不能是负数";
   else if($n==0||$n==1)
       $out=1;
   else $out=f($n-1)*$n; 
   return $out;
}

echo f(6);

?>
五、将字符串反转,比如 “abcdefg” 转化为 "gfedcba"
1、如果面试者使用 C 语言效果最佳
2、可以进一步考察这种形式的反转算法, www.ucai.cn => cn.ucai.www

<?php
    $str = "hello";
 
    function fan($str) {
        //声明一个临时的变量
        $n = "";
        //获取字符串长度
        $m = strlen($str)-1;
        for($i=$m; $i >= 0;  $i--) {
            $n .= $str{$i};
        }  
        return $n;
    }
    echo fan($str);
?>

支持中文:
<?PHP
   
    function getRev($str,$encoding='utf-8'){
        $result = '';
        $len = mb_strlen($str);
        for($i=$len-1; $i>=0; $i--){
            $result .= mb_substr($str,$i,1,$encoding);
        }
        return $result;
    }
    $string = 'OK你是正确的Ole';
    echo getRev($string);

?>

六、求出 IPV4 IP地址所对应的整数,比如 192.168.199.1 对应整数 3232286465
1、可以先让其求字符串所对应的整数这个简单算法
2、如果面试者使用 C 语言效果最佳

<?php
$ip = gethostbyname('www.sharejs.com');
$out = "The following URLs are equivalent:<br />\n";
$out .= 'http://www.sharejs.com/, http://' . $ip . '/, andhttp://' . sprintf("%u",

ip2long($ip)) . "/<br />\n";
echo $out;
?>
这是如何计算的,目前我知道有两个算法。

其一
<?php
function ip2int($ip){
    //我们先把ip分为四段,$ip1,$ip2,$ip3,$ip4
    list($ip1,$ip2,$ip3,$ip4)=explode(".",$ip);
    //然后第一段乘以256的三次方,第二段乘以256的平方,第三段乘以256
    //这即是我们得到的值
    return $ip1*pow(256,3)+$ip2*pow(256,2)+$ip3*256+$ip4;
}
?>

其二,用位运算
<?php
function ip2int($ip){
    list($ip1,$ip2,$ip3,$ip4)=explode(".",$ip);
    return ($ip1<<24)|($ip2<<16)|($ip3<<8)|($ip4);
}
?>
我们会发现,有些ip转化成整数后,是负的,这是因为得到的结果是有符号整型,最大值是2147483647.

要把它转化为无符号的,可以用
sprintf("%u",ip2long($ip);
就能转换为正整数。而且得到的结果用long2ip也可以正常转换回原来的ip地址。也可以用ip2long来验

证一个ip是否是有效的,如
<?php
function chk_ip($ip){
    if(ip2long($ip)=="-1") {
       return false;
    }
    return true;
}
//应用
var_export(chk_ip("10.111.149.42"));
var_export(chk_ip("10.111.256.42"));
?>
将输出true和false


七、使用最高效的算法,将一堆100以内的数排序,不能使用排序的库函数
1、不允许使用现成的各种排序算法
2、要求一遍遍历完成即实现排序
3、也可以问:如何对n个数进行排序,要求时间复杂度O(n),空间复杂度O(1)
看上去似乎任何已知的算法都无法做到,如果谁做到了,那么所有的排序方法:QuickSort,ShellSort

,HeapSort,BubbleSort等等等等,都可以扔掉了,还要这些算法干吗阿,呵呵。不过实际上,在数字

范围有限制的情况下,是有一个这样的算法的,只需要用一个数组记录每个数字出现次数就可以了。

假定你的数字范围在0到65535范围之内,定义一个数组count[65536](这个空间是常量,和n无关,所以

是O(1) ),初值全部为0。
那么假设有下面这些数字:
100
200
300
119
0
6
...
那么对于每个这个数字,都做在count中记录一下:
100 => count[100]++
200 => count[200]++
300 => count[300]++
119 => count[119]++
0 => count[0]++
6 => count[6]++
...
最后,遍历一边所有这些数字就可得到0~65535每个数字的个数(在count数组中),然后再顺序遍历

count数组,count[n] = m,则输出m个n,(比如说有count[3] = 2, 那么说明有2个数字3),依次输出

,最后可得结果。第一次遍历是O(n),第二次遍历是O(1),为常量,所以最后的时间复杂度为O(n),而

空间复杂度为O(1)

#include
int main()
{
int a[] = {10,6,9,5,2,8,4,7,1,3};
int len = sizeof(a) / sizeof(int);
int temp;
for(int i = 0; i < len; )
{
temp = a[a[i] – 1];
a[a[i] – 1] = a[i];
a[i] = temp;
if ( a[i] == i + 1)
i++;
}
for (int j = 0; j < len; j++)
cout< return 0;
}

这个算法很简单,相信大家都会,只是这个题太过于变态了,一般会把面试者吓住

八、有上千万个1000万以内的数据,请排除掉重复的数
1、可以转化为找出重复的数
2、要求空间最省
3、要求一次遍历完成整个查找
4、延伸:如果用 Shell 命令实现怎么办?通过awk去除重复行
100万条,也就是16M而已,内存顶得住的。
遍历一遍,在内存里构造一个该数据的hash表,就搞定了。
参考:
1、怎么在海量数据中找出重复次数最多的一个?
   方案1:先做hash,然后求模映射为小文件,求出每个小文件中重复次数最多的一个,并记录重复

次数。然后找出上一步求出的数据中重复次数最多的一个就是所求(具体参考前面的题)。
2、上千万或上亿数据(有重复),统计其中出现次数最多的钱N个数据。
  方案1:上千万或上亿的数据,现在的机器的内存应该能存下。所以考虑采用hash_map/搜索二叉树/

红黑树等来进行统计次数。然后就是取出前N个出现次数最多的数据了,可以用第2题提到的堆机制完成

九、如果从1000万行左右的文件中,随机地取出 10万行左右的样本数据
1、要求一遍文件扫描完成数据获取
2、空间最省,将结果输出在另外一个文件中
3、可以要求写出完整程序,包括 fopen 的使用等

十、字符串库函数的相关实现思路
1、检测一个字符串是否包含在另一个字符串中
2、实现 trim 函数、strlen 函数
3、复杂一些的:求出给定字符串中最长的回文字符的长度以及把它们给输出来。

strpos($a, $b) !== false 如果$a 中存在 $b,则为 true ,否则为 false。
用 !== false (或者 === false) 的原因是如果 $b 正好位于$a的开始部分,那么该函数会返回int

(0),那么0是false,但$b确实位于$a中,所以要用 !== 判断一下类型,要确保是严格的 false。
其它的还有 PHP 原生支持的函数,如 strstr(),stristr() 等,直接判断就可以了。

通过正则表达式替换,功能更强
php去除字符串首尾空格(包括全角)
  复制代码 代码如下:

  <?
$str="          ";
$str = mb_ereg_replace('^( | )+', '', $str);
$str = mb_ereg_replace('( | )+$', '', $str);
echo mb_ereg_replace('  ', "\n  ", $str);
?>


计字串长度:
while ( isset($str{$i}) && ++$i );

0 0