ホームページ > バックエンド開発 > PHPチュートリアル > PHP 面接の質問がまとめられ、共有される

PHP 面接の質問がまとめられ、共有される

小云云
リリース: 2023-03-22 11:56:01
オリジナル
4426 人が閲覧しました

この記事は主に PHP 面接の質問の収集と共有を共有し、皆さんが面接をよりスムーズに行えるようにすることを願っています。

サーバーの側面

1. nginx のスムーズな再起動

nginx は新しいワーカー プロセスを実行し、古いワーカー プロセスを静かにシャットダウンし、リッスンしているソケットを閉じるようにワーカー プロセスに通知しますが、現在接続している顧客にはサービスを提供し続けます。すべてのクライアント サービスが完了すると、古いワーカー プロセスは
閉じられます。新しい設定ファイルの適用が失敗した場合でも、nginx は古い設定ファイルを使用して動作し続けます。
簡単に言うと、nginx は前のリクエストの処理を継続し、新しいリクエストを処理するために新しいプロセスを開始します。処理が完了すると、古いプロセスは強制終了されます。

2. ファイルの最後の 10 行を取得します。
tail -10 a.log

3. より多くのシステムリソースを占有しているプロセスを確認します
Top -n '私は検索したいキーワードです' a.txt Cut -d ":" - f1

行を数えるファイル内に出現するキーワード:
grep -n "keyword" "file path" | Cut -d ":" -f1
統計ファイル内でキーワードが出現する最後の行番号:
grep -n "keyword"ファイル パス" | tail -n 1 |cut -d ":" -f1


4 、 /root/ ディレクトリでキーワード "www" を持つファイルを検索し、ターミナルでコマンドを実行します:
find /root / –type f | xargs grep “www

5. ファイルの行数を数えます
wc -l a .txt

デモディレクトリ内の js ファイルの数を数えます:
find Demon/ -name "*.js" | wc -l
デモディレクトリ内のすべての js ファイルのコード行数を数えます:
find Demon/ -name "*.js " |xargs cat|wc -l
wc -l `find ./ -name "*. js"`|tail -n1
デモ ディレクトリ内のすべての js ファイルのコード行数を数え、空の行を除外します。
find /demo - name "*.js" |xargs cat|grep -v ^$|wc -l

6. ファイルのリアルタイム監視
tail -f a.log

7. nginx ログ内の最も訪問された 100 の IP と訪問数
最も訪問された 100 の IP と訪問数nginx ログ
awk '{print $1}' /opt/software/nginx/logs/access.log | sort -n -k 1 -r head -n 100
8.コンパイルしたphpに
----------------------------------------
ソースコードのインストール
1. phpのソースコードディレクトリを見つけます
2. EXTディレクトリにジャンプします
3. phpizeを実行してconfigureファイルを生成します
4. ./configure --with-php-config =/usr/local/php/bin/ php-config
5. make
をコンパイルします 6. make installをコンパイルしてインストールします
7. php.ini extension=/usr/local/***.so
を変更します 8. php-fpm

YUMインストールを再起動します:
1. PHP の公式 Web サイトにアクセスしてソースコードをダウンロードします (htpp://pecl.php.net)
2. ファイルを解凍します
3. phpize を実行して設定ファイルを生成します
4. ./configure --with-php -config =/usr/local/php/bin/php-config
5. make
をコンパイルします 6. make install
をコンパイルしてインストールします 7. php.ini extension=/usr/local/***.so
を変更します 8. phpを再起動します-fpm
-------------------------------------------------
php最適化nginx最適化mysql最適化

php最適化:
1. クラスメソッドを静的として定義します。
2. 一重引用符を使用してみてください。
3. php-fpm プロセスの数を変更します。
4. 単一スクリプトの最大使用可能メモリを変更します。
5. 大きなアレイは使用後すぐに解放する必要があります。
6. ループする場合、ループの最大数を設定します
7. エラーをシールドするために @ を使用しないでください
9. require_once の代わりに require を使用してください

:
1. nginx 子プロセスの数を変更します。 [最大 65535]
2. 静的キャッシュを有効にする
3. メインプロセスの数を変更します。 CPU の数に応じて、通常はその倍数で指定することをお勧めします (例: クアッドコア CPU 2 個は 8 個としてカウントされます)
4. gzip 出力をオンにする [gzip がオンになっている場合、ob 関数は使用できません]
5. keepalive_timeout は接続タイムアウトを設定します

MySQL の最適化:
1. 連続した読み取りと書き込みを回避します
4. select * を設定します。フィールドの型を適切に設定する
7. 読み取りと書き込みを分離する
8. パーティション化とサブテーブルを作成する
10. リソースを消費する操作を避ける
11. rand() を使用しないようにします。またはクエリ
13. データの一部をクエリする LIMIT 1 を追加します
14. 初期段階でデータの適切な評価を実行し、テーブルを分割して分割します
16. % を使用したファジー クエリを回避します。プレフィックス
17. mysql の組み込み関数の使用を避ける
18. クエリが遅いという問題を解決するために複数のスレーブを使用する

フラッシュ セールを実装するにはどうすればよいですか?

私たちが行う同時フラッシュセールの数は数十万で、以下のバージョンは数十万です:

1. 特にフラッシュセールサーバーの場合 [追記: ボリュームが大きい場合は必要ありません。 ]
2. 静的ページを生成します。 [ ps: まだ大きい場合は、このファイルを cdn に置くことができます ]
3. カウントダウンとインベントリはサーバーから取得されます [一定期間内に 1 回のみ取得されます。カウントダウンが終了すると、サーバーは開始したかどうかを確認するように要求されます] 4. 販売するデータベースを redis に保存します [ key value] Stock=10
5. Redisキューを設定します [リストをキューとして使用] lpop rpush
6. ユーザーがリクエストを行うと、ユーザーがフラッシュセールに参加しているかどうかが判断されます。データがキューに書き込まれると同時に、インベントリが 1 減ります。ユーザーが参加している場合は、「すでに参加しています」というメッセージが表示されます
PS: このセクションでは、redid のアトミック操作と、トランザクション multi および watch を使用します。
Redis の楽観ロック cas ==== は設定前に値が変化したかどうかを判断するためのものです
7. 在庫が 0 減るとフラッシュセールを実行できなくなります
8. 非同期スクリプト処理キューデータ [crontab + phpファイル】

10,000〜30,000と言われれば、別途サーバーをレンタルする必要はありません

ビジネス関連の質問をされたら、臨機応変に対応しましょう! ! ! !

例: 10 人のユーザーが購入したが支払いをしなかった場合はどうすればよいですか?
最初の発言:
当時の商品の需要は、お金を払わなくても問題なく、他のユーザーは購入できないというものだったとのことで、当時の商品とその商品がどうかについて話し合いました。通常、ユーザーは安かったので支払うでしょう
2 つの説明:
は次のフラッシュ セールを開始します。 たとえば、Xiaomi の場合、2 時間後も購入し続けることができます。 !
3 番目の停留所:
はい。 。 。 。

買われすぎないようにするにはどうすればよいですか?
在庫を減らす場合、それはアトミックな操作であり、cas オプティミスティック ロックを使用します。テスト中、買われすぎの状況はありませんでした

また、フラッシュセールではショッピングカートは必要なく、クリックすると行列ができます


Q1: ブラッシングを防ぐにはどうすればよいですか?通常、ラッシュセール時には大幅な割引が行われます。誰かが悪意を持って不正行為を行った場合、一般ユーザーは購入の機会を失います。たとえば、スナップアップされている製品の数が 1,000 で、誰かが悪意を持って 900 をスワイプした場合、通常のユーザーが取得できるのは 100 だけです。
その後の支払いプロセスで悪意を持って取得された 900 が確認された後、スナップアップ時間が経過している可能性があります。たとえ悪意を持って掴まれた900がすべて無事に支払われたとしても、それは通常のユーザーにとって不公平です。
このビジネスシナリオでは、私たちが行うことは商品を表示し、商品を購入する権利を発行することです。実際の消費は第三者によって行われます。次に、ユーザー詐欺の問題は、当社とサードパーティの支払いページによって制御される必要があります。ユーザーがキューイングメカニズムを通じて購入割り当てを取得し、第三者にジャンプした後、当社は、第三者と合意した暗号化方法に従って暗号化された情報を転送します。第三者は、暗号化された情報を暗号化解除した場合にのみ、ユーザーに支払いを許可します。合意された復号化方法。 暗号化 復号化プロセスには、ライフサイクルのあるコンテンツが含まれる場合があります。このように、ユーザーが高頻度リクエストの支払いページで商品を取得する場合、実際には、1) 暗号化されたペア、2) 初回のみを通じて商品を取得できます。ただし、サードパーティは商品を販売することが目的であるため、この種の協力の成功率は低いです。悪意のあるブラッシングにより、ビジネスレベルで製品が在庫切れであることが実際に示されます。結果として、購入したいユーザーは機会を失いますが、第三者に損害を与えることはありません。ビジネス層でこのようなブラッシング状況を避けたい場合、これは一般的なスパム対策の問題だと思います。これについては本当によくわかりません。

Q2: ブラシを正確に配置したい場合、多くの判断要素があり、ロジックはこれに反して複雑です。急ぎの購入には迅速な対応が必要です。
はい、人気商品の緊急購入はリクエストのプレッシャーが高く、同時実行性が高いため、緊急購入ビジネスではロジックを追加しすぎたり、バックエンドに過度に依存したりすべきではありません。シンプルであればあるほど、効果は高くなります。システムを設計する場合、システムだけではカバーできないことがたくさんあります。システムが適切に動作するためには、いくつかの前提条件となるモジュールと機能を準備する必要があります。アカウント システムとユーザーの消費記録を構築することをお勧めします。
Q3: 調整は商品の在庫を第三者と比較するだけですか?
調整は実際には消費データの比較です。今日の統計で合計値が Y の X 個のアイテムの消費が示される状況を回避するために、サードパーティは、合計値が M で N 個のアイテムの消費を示します。金額の不一致による決済や共有などのトラブルは避けてください。
あなたの質問にある在庫差分の問題では、サードパーティが当社のデータ層のインターフェースを通じて提供する製品を定期的に更新する必要があると思います。実際、当社の製品ライブラリでは、必ずしもサードパーティのみが製品を提供できるわけではありません。たとえば、果物を販売するサードパーティと協力する場合、インターフェイスを通じてサードパーティが製品を削減できるようにすることもできます。サードパーティは先週、アイテムが 100 個あると発表しましたが、今週はオフラインが暑いため、残りは 20 個しかありません。サードパーティがより低い値に更新できるようにする必要もあります。しかし、この方法では、システムはさらに複雑になります。

Q4: 望ましい結果が得られないサードパーティのプロモーションの問題を回避するためのアンチブラッシング。
はい、ユーザー ID ディメンションと IP ディメンションはどちらも効果的な方法です。具体的なシナリオを見てみましょう。アカウント システムを使用している企業の場合、ユーザー ID ディメンションを使用して各ユーザーの購入記録を記録し、管理することが最も効果的です。市販のECサイトは、基本的に急ぎ買いの場合はログインが必要で、商品ごとに1人での購入数を制限しているのですが、実際にはユーザーの消費量を保存・記録し、消費前のクエリを再度生成して追加しています。それを制御するコードロジック。

Q5: ラッシュセールイベントごとに新しい認証コードが必要ですか?
検証コードはチューリングテストです。テスト方法が適切であり、毎回生成される検証情報が決して出現しないことが保証されており、不規則である限り、それは優れた検証コードです。

膨大なデータの中から繰り返し回数が最も多いものを見つける方法

ユーザーのIPはWebサイトのログに記録されており、最も訪問数が多いIPを見つけます

1kwのID番号とそれに対応するデータがあるとします。 ID 番号は重複する場合があるため、最も多く出現する ID 番号を見つける必要があります。

サイズが 1G のファイルがあり、その各行はワードであり、ワードのサイズは 16 バイトを超えず、メモリ制限は 1M です。最も頻繁に使用される 100 個の単語を返します。

ファイルは 10 個あり、各ファイルは 1G であり、各ファイルの各行にユーザーのクエリが格納されます。クエリの頻度で並べ替えるように求められます。

バブルソート:
原則:
最初の数値をすべての数値と比較し、大きな交換位置に遭遇したため、最初に最大の数値が最後に配置され、2 回目で比較を続けます。最初の比較では、最後の数値は最大であると判断されたため比較されません。などです。

1. バブルソート法

 *     思路分析:法如其名,就是像冒泡一样,每次从数组当中 冒一个最大的数出来。 
 *     比如:2,4,1    // 第一次 冒出的泡是4 
 *                2,1,4   // 第二次 冒出的泡是 2 
 *                1,2,4   // 最后就变成这样
ログイン後にコピー

時間計算量:
バブルソートは、時間をスペースと交換するソート法です。最悪のシナリオは、順序を逆順に変更するか、逆順を順に変更することです。

$arr=array(1,43,54,62,21,66,32,78,36,76,39);  
function getpao($arr)
{  
  $len=count($arr);
  //设置一个空数组 用来接收冒出来的泡
  //该层循环控制 需要冒泡的轮数
  for($i=1;$i<$len;$i++)
  { //该层循环用来控制每轮 冒出一个数 需要比较的次数
    for($k=0;$k<$len-$i;$k++)
    {
       if($arr[$k]>$arr[$k+1])
        {
            $tmp=$arr[$k+1];
            $arr[$k+1]=$arr[$k];
            $arr[$k]=$tmp;
        }
    }
  }
  return $arr;
}
ログイン後にコピー

2. 選択項目の並べ替え:

http://jingyan.baidu.com/article/f3ad7d0f07516d09c3345b19.html
http://mmm2010.blog.163.com/blog/static/174230348201292273310140/
function select_sort($arr) {
//实现思路 双重循环完成,外层控制轮数,当前的最小值。内层 控制的比较次数
    //$i 当前最小值的位置, 需要参与比较的元素
    for($i=0, $len=count($arr); $i<$len-1; $i++) {
        //先假设最小的值的位置
        $p = $i;
        //$j 当前都需要和哪些元素比较,$i 后边的。
        for($j=$i+1; $j<$len; $j++) {
            //$arr[$p] 是 当前已知的最小值
            if($arr[$p] > $arr[$j]) {
     //比较,发现更小的,记录下最小值的位置;并且在下次比较时,
 // 应该采用已知的最小值进行比较。
                $p = $j;
            }
        }
        //已经确定了当前的最小值的位置,保存到$p中。
 //如果发现 最小值的位置与当前假设的位置$i不同,则位置互换即可
        if($p != $i) {
            $tmp = $arr[$p];
            $arr[$p] = $arr[$i];
            $arr[$i] = $tmp;
        }
    }
    //返回最终结果
    return $arr;
}
3.快速排序法  
function quick_sort($arr) {
    //先判断是否需要继续进行
    $length = count($arr);
    if($length <= 1) {
        return $arr;
    }
    //如果没有返回,说明数组内的元素个数 多余1个,需要排序
    //选择一个标尺
    //选择第一个元素
    $base_num = $arr[0];
    //遍历 除了标尺外的所有元素,按照大小关系放入两个数组内
    //初始化两个数组
    $left_array = array();//小于标尺的
    $right_array = array();//大于标尺的
    for($i=1; $i<$length; $i++) {
        if($base_num > $arr[$i]) {
            //放入左边数组
            $left_array[] = $arr[$i];
        } else {
            //放入右边
            $right_array[] = $arr[$i];
        }
    }
    //再分别对 左边 和 右边的数组进行相同的排序处理方式
    //递归调用这个函数,并记录结果
    $left_array = quick_sort($left_array);
    $right_array = quick_sort($right_array);
    //合并左边 标尺 右边
    return array_merge($left_array, array($base_num), $right_array);
}
ログイン後にコピー

4. 挿入の並べ替え方法

シナリオの説明:

生徒が何度も試みて失敗するたびに、教師はそれを発見しました。ソート チームを終えた後、私はクラスのほとんどで遅れて、「もうバブリングする必要はない、ちょっとアウトだ、今日はソートを入れよう。」と言いました。
この時、体育の先生が数学の先生の役割を担って、生徒たちに並び方・挿入並べ替えを指導しました。
1. 最初のクラスメートをベンチマークとして開始し、2 番目のクラスメートが前に進み、最初のクラスメートよりも高ければ静止し、低ければ 3 番目のクラスメートが最初に位置を変更します。前の生徒と比較してください。2 番目の生徒と比較し、それが低い場合は 2 番目の生徒と切り替え、次に最初の生徒と前方に比較し、低い場合は再度切り替えます。そうでない場合はブロックし、比較しません
3.ステップ 2 を前から後ろに実行し、各生徒が前のクラスメートと比較して挿入するのに適した位置を見つけ、他の生徒が適切な位置に戻ります。つまり、前のクラスメートと同じか、または挿入します。自分の身長よりも低く、後者のクラスメートは自分の身長より高い
によると、このようにして、生徒は正しい位置を 1 つずつ見つけることができ、毎回隣接するものを比較する必要がなくなり、位置を見つけた後、前と比較する必要はありません...

挿入ソート方法のアイデア: ソート対象の項目をソートする ソート番号が仮定された指定された位置に要素が配列に挿入されます。

function insert_sort($arr) {
    //区分 哪部分是已经排序好的
    //哪部分是没有排序的
    //找到其中一个需要排序的元素
    //这个元素 就是从第二个元素开始,到最后一个元素都是这个需要排序的元素
    //利用循环就可以标志出来
    //i循环控制 每次需要插入的元素,一旦需要插入的元素控制好了,
    //间接已经将数组分成了2部分,下标小于当前的(左边的),是排序好的序列
    for($i=1, $len=count($arr); $i<$len; $i++) {
        //获得当前需要比较的元素值。
        $tmp = $arr[$i];
        //内层循环控制 比较 并 插入
        for($j=$i-1;$j>=0;$j--) {
   //$arr[$i];//需要插入的元素; $arr[$j];//需要比较的元素
            if($tmp < $arr[$j]) {
                //发现插入的元素要小,交换位置
                //将后边的元素与前面的元素互换
                $arr[$j+1] = $arr[$j];
                //将前面的数设置为 当前需要交换的数
                $arr[$j] = $tmp;
            } else {
                //如果碰到不需要移动的元素
           //由于是已经排序好是数组,则前面的就不需要再次比较了。
                break;
            }
        }
    }
    //将这个元素 插入到已经排序好的序列内。
    //返回
    return $arr;
}
/**
     * 插入排序,默认第一位已经排好序,从第二位开始依次向前比较,确定自己的位置后插入,即前一位小余或等于当前,且后一位大于当前。
     * 插入后,自己新位置后面的元素依次向后移位, 完成一轮插入排序
     * @param arr
     * @return
     */
    public static int[] insertSort(int[] arr) {
        int len = arr.length;
        for (int i = 1; i < len; i++) {
            if (arr[i - 1] > arr[i]) {
                int k = arr[i];
                int j = i;
                while (j > 0 && arr[j - 1] > k) {
                    arr[j] = arr[j - 1];
                    j--;
                }
                arr[j] = k;
            }
        }
        return arr;
    }
ログイン後にコピー


1,2,3,4,5,6,7
今7を見つけたいです

まず真ん中の数字4

を取り出して、それが探している数字であるかどうかを判断します。それは小さいです
それから右に行って検索してください
それから右側の数字をすべて取り出してください
その中の真ん中の数字6を取り出してください
まだ小さいことがわかりました
引き続き右側の配列を探してください
見つけました7、わかりました! ! !

最悪のシナリオは、この番号が存在しないことです =====

 1 <?php
 2     #二分查找
 3     function binarySearch(Array $arr, $target) {
 4         $low = 0;
 5         $high = count($arr) - 1;
 6         
 7         while($low <= $high) {
 8             $mid = floor(($low + $high) / 2);
 9             #找到元素
10             if($arr[$mid] == $target) return $mid;
11             #中元素比目标大,查找左部
12             if($arr[$mid] > $target) $high = $mid - 1;
13             #重元素比目标小,查找右部
14             if($arr[$mid] < $target) $low = $mid + 1;
15         }
16         
17         #查找失败
18         return false;
19     }
20     
21     $arr = array(1, 3, 5, 7, 9, 11);
22     $inx = binarySearch($arr, 1);
23     var_dump($inx);
24 ?>
ログイン後にコピー

安全方面:
xss :跨站脚本攻击
csrf : 跨站请求伪造
Ddos:用很多机器对网址进行请求,把服务器某方面搞挂。
sql注入: 通过关键字或者非法字符的注入,实现一些对数据库一些非正常的操作

最简单的demo :
在用户登陆的时候,用户名和密码的判断,密码后加上 or 1=1

如何防止sql注入:
关键字的过滤
pdo预处理
php 配置文件 php.ini 中的 magic_quotes_gpc选项没有打开,被置为 off
addslashes stripslashes
mysql_real_escape_string
对一些数据类型做强制的校验

如何防止xss攻击?
xss攻击最简单的方式就是通过地址栏输入<script></script>,最简单的列子我们在php在使用一个get的a参数的时候,如何客户端传过来是<script>alert(1)</script>,
这样的话就会在我们的浏览器弹出来1,如果是页面的跳转,或者是一些其它脚本、病毒的话,可能对我们网站的安全造成很大的隐患。

最简单的解决办法
不要相信客户端的任何输入,在程序做严格的判断以及处理
htmlspecialchars进行过滤

csrf :
这个我们在学curl的时候做的模拟登陆就是跨站请求伪造!!!!
最简单的大白话就是:
a网站往b网站请求数据。
加个token防止下就行了,简单,粗暴,有效

Dos和Ddos防止:
阿里云 高防ip
idc机房
放弃一部分请求不处理。


正则方面的问题:

贪婪模式和非贪婪模式的区别:
贪婪模式匹配到内容之后会继续向后匹配
非贪婪模式则不回继续匹配


匹配中文字符的正则表达式: [\u4e00-\u9fa5]
评注:匹配中文还真是个头疼的事,有了这个表达式就好办了
匹配双字节字符(包括汉字在内):[^\x00-\xff]
评注:可以用来计算字符串的长度(一个双字节字符长度计2,ASCII字符计1)
匹配空白行的正则表达式:\n\s*\r
评注:可以用来删除空白行
匹配HTML标记的正则表达式:<(\S*?)[^>]*>.*?|<.*? />
评注:网上流传的版本太糟糕,上面这个也仅仅能匹配部分,对于复杂的嵌套标记依旧无能为力
匹配首尾空白字符的正则表达式:^\s*|\s*$
评注:可以用来删除行首行尾的空白字符(包括空格、制表符、换页符等等),非常有用的表达式
匹配Email地址的正则表达式:\w+([-+.]\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*
评注:表单验证时很实用
匹配网址URL的正则表达式:[a-zA-z]+://[^\s]*
评注:网上流传的版本功能很有限,上面这个基本可以满足需求
匹配帐号是否合法(字母开头,允许5-16字节,允许字母数字下划线):^[a-zA-Z][a-zA-Z0-9_]{4,15}$
评注:表单验证时很实用
匹配国内电话号码:\d{3}-\d{8}|\d{4}-\d{7}
评注:匹配形式如 0511-4405222 或 021-87888822
匹配腾讯QQ号:[1-9][0-9]{4,}
评注:腾讯QQ号从10000开始
匹配中国邮政编码:[1-9]\d{5}(?!\d)
评注:中国邮政编码为6位数字
匹配身份证:\d{15}|\d{18}
评注:中国的身份证为15位或18位
匹配ip地址:\d+\.\d+\.\d+\.\d+
评注:提取ip地址时有用
匹配特定数字:
^[1-9]\d*$    //匹配正整数
^-[1-9]\d*$   //匹配负整数
^-?[1-9]\d*$   //匹配整数
^[1-9]\d*|0$  //匹配非负整数(正整数 + 0)
^-[1-9]\d*|0$   //匹配非正整数(负整数 + 0)
^[1-9]\d*\.\d*|0\.\d*[1-9]\d*$   //匹配正浮点数
^-([1-9]\d*\.\d*|0\.\d*[1-9]\d*)$  //匹配负浮点数
^-?([1-9]\d*\.\d*|0\.\d*[1-9]\d*|0?\.0+|0)$  //匹配浮点数
^[1-9]\d*\.\d*|0\.\d*[1-9]\d*|0?\.0+|0$   //匹配非负浮点数(正浮点数 + 0)
^(-([1-9]\d*\.\d*|0\.\d*[1-9]\d*))|0?\.0+|0$  //匹配非正浮点数(负浮点数 + 0)
评注:处理大量数据时有用,具体应用时注意修正
匹配特定字符串:
^[A-Za-z]+$  //匹配由26个英文字母组成的字符串
^[A-Z]+$  //匹配由26个英文字母的大写组成的字符串
^[a-z]+$  //匹配由26个英文字母的小写组成的字符串
^[A-Za-z0-9]+$  //匹配由数字和26个英文字母组成的字符串
^\w+$  //匹配由数字、26个英文字母或者下划线组成的字符串

下面是一些特殊字符:
正则表达式中的特殊字符: (学习参考书-<<精通正则表达式>>)
字符
意味: 文字の場合、通常は文字通りの意味を意味し、説明のない次の文字が特殊文字であることを示します。
例: /b/ は文字「b」に一致します。b の前にバックスラッシュを追加すると、つまり /b/ となり、その文字は特殊文字になり、
が単語の分割線に一致することを示します。
または:
いくつかの文字については、通常、それらが特別であると述べられ、次の文字が特別ではなく、文字通りに解釈されるべきであることを示します。
例: * は特殊文字で、任意の数の文字 (0 文字を含む) に一致します。たとえば、/a*/ は 0 個以上の a に一致することを意味します。
リテラル * に一致するには、a の前にバックスラッシュを追加します。たとえば、/a*/ は 'a*' に一致します。

Character^
意味: 一致する文字が先頭になければならないことを示します。
例: /^A/ は、「an A」の「A」とは一致しませんが、「An A.」の最初の「A」と一致します。

文字 $
意味: ^ と同様、最後の文字と一致します。
例: /t$/ は、「eater」の「t」とは一致しませんが、「eat」の「t」とは一致します。

文字 *
意味: * より前の文字と 0 回または n 回一致します。
例: /bo*/ は、「A ghost booooed」の「boooo」または「A Bird warbled」の「b」に一致しますが、「A goat g
runted」の文字には一致しません。

文字 +
意味: + 記号の前の文字と 1 回または n 回一致します。 {1,} と同等。
例: /a+/ は、「candy」の「a」と「caaaaaaandy」のすべての「a」に一致します。

文字?
意味: 0 回または 1 回前の文字と一致します。
例: /e?le?/ は、「angel」の「el」と「angle.」の「le」に一致します。

文字。
意味: (小数点) は改行文字を除くすべての単一文字に一致します。
例: /.n/ は、「いいえ、リンゴが木の上にあります」の 'an' と 'on' には一致しますが、'nay' には一致しません。


文字 (x)
意味: 'x' と一致し、一致する値を記録します。
例: /(foo)/ は、「foo bar」の「foo」と一致し、記録します。一致する部分文字列は、結果配列の要素 [1]、...、[n] によって、または RegExp オブジェクトのプロパティ $1、...、$9 によって返されます。

文字 x|y
意味: 'x' または 'y' と一致します。
例: /green|red/ は、「green apple」の「green」と「red apple」の「red」に一致します。

文字 {n}
意味: ここでの n は正の整数です。最初の n 文字と一致します。
例: /a{2}/ は、「candy」の「a」とは一致しませんが、「caandy」のすべての「a」と、「caaandy.」の最初の 2 つの
'a には一致します。

文字 {n,}
意味: ここでの n は正の整数です。少なくとも n 個前の文字と一致します。
例: /a{2,} は、「candy」の「a」には一致しませんが、「caandy」のすべての「a」と「caaaaaaandy」のすべての「a」に一致します。

文字 {n,m}
意味: ここでの n と m は両方とも正の整数です。少なくとも n 個、最大で m 個前の文字と一致します。
例: /a{1,3}/ は、「cndy」のどの文字とも一致しませんが、「candy,」の「a」、「caandy,」の最初の 2 つの「a」と「caaaaaaaandy」には一致します。 「caaaaaaandy」の最初の 3 つの「a」に注意してください。「caaaaaaandy」に多くの「a」がある場合でも、一致するのは最初の 3 つの「a」、つまり「aaa」のみです。

Character [xyz]
意味: リスト内の任意の文字と一致する文字のリスト。ハイフン - を使用して文字の範囲を指定できます。
例: [abcd] は [a-c] と同じです。これらは、「brisket」の「b」と「ache」の「c」に一致します。

Character[^xyz]
意味: 1 文字の補数。つまり、リストされた文字を除くすべてに一致します。 ハイフンを使用して、
文字の範囲を示すことができます。
例: [^abc] と [^a-c] は同等で、最初に「brisket」の「r」と「chop.」の「h」に一致します。

文字
意味: スペースに一致します (b と混同しないでください)

文字 b
意味: スペースなどの単語の分割線に一致します (b と混同しないでください)
例: /bnw/ /wyb/ は「noonday」の「no」に一致し、/wyb/ は「おそらく昨日」の「ly」に一致します。

文字 B
意味: 単語の非改行行と一致します
例: /wBn/ は「正午」の「on」と一致し、/yBw/ は「おそらく昨日」の「ye」と一致します。

Character cX
意味: ここの X は制御文字です。制御文字の文字列と一致します。
例: /cM/ は文字列内の control-M と一致します。

文字 d
意味: [0-9] に相当する数値と一致します。
例: /d/ または /[0-9]/ は、「B2 はスイート番号です」の「2」と一致します。

文字 D
意味: [^0-9] に相当する、数値以外の任意の文字に一致します。
例: /D/ または /[^0-9]/ は、「B2 はスイート番号です。」の「B」と一致します。

文字 f
意味: 形式文字と一致します

文字 n
意味: 改行文字と一致します

文字 r
意味: 復帰文字

文字 s と一致します
意味: [fnrtv] に相当する、スペース、タブ、フォーム フィード、改行文字を含む単一の空白文字と一致します。
例: /sw*/ は、「foo bar.」の「bar」と一致します。

文字 S
意味: [^ fnrtv] に相当する、空白を除く 1 つの文字と一致します。
例: /S/w* は、「foo bar.」の「foo」に一致します。

Character t
意味: タブ文字と一致します

Character v
意味: 先頭のタブ文字と一致します

Character w
意味: [A-Za-z0 -9_] に相当する、すべての数字、文字、アンダースコアと一致します。
例: /w/ は、「apple,」の「a」、「$5.28」の「5」、「3D.」の「3」に一致します。

文字 W
意味: [^A-Za-z0-9_] に相当する、数字、文字、アンダースコアを除く他の文字と一致します。
例: /W/ または /[^$A-Za-z0-9_]/ は、「50%.」の '%' に一致します。

文字 n
意味: ここでの n は正の整数です。正規表現の最後の部分文字列に一致する n の値 (左括弧をカウントします)。


PHP関数に関する質問:

1.配列関数

array_key_exists はキーが存在するかどうかを決定します
is_array はそれが配列であるかどうかを決定します
in_array は指定された値がデータに現れるかどうかを決定します
array_count_values は回数を決定します値が表示されます
array_search 配列検索
array_merge 配列のマージ
array_map 配列の各要素にユーザー定義関数を使用します
array_change_case 配列キーの大文字と小文字を変更します
sort 配列の並べ替え
array_push 配列の末尾に 1 つ以上の要素を挿入しますarray
array_pop 配列の最後の要素をポップします
array_unshift 配列の先頭に複数の要素を挿入します
array_shift 配列の最初の要素をポップします
implode 配列を文字列に変換します
shuffle 配列の順序を乱します
array_rand 配列から複数の要素をランダムに削除します配列
array_chunk 配列を新しい配列に分割
array_diff 差分
array_inestsert 交差
array_flip キー値を交換
array_keys 配列のすべてのキーを返す
count 配列の長さを計算

2 文字列関数
addcslashes — バックスラッシュ エスケープを追加します。文字を文字列内の一部の文字に変換します
addslashes — 指定されたメソッドを使用して文字を変更します 文字列内の文字をエスケープします
bin2hex — バイナリデータを 16 進数表現に変換します
chop — rtrim() のエイリアス関数
chr — ASCII コードを返します文字の分割
chunk_split — 特定の文字長に従って文字列を小さな部分に分割
convert_cyr_string — キリル文字を他の文字に変換
convert_uudecode — 文字列を復号化
convert_uuencode — 文字列を暗号化
count_chars — 文字列内の文字使用情報を返す
crc32 — 文字列の crc32 を計算します 多項式
crypt — 一方向ハッシュ暗号化関数
echo — 一部のコンテンツを表示するために使用されます
explode — 区切り文字を使用して文字列を配列に変換します
fprintf — 必要に応じてデータを返し、それを直接書き込みますドキュメント ストリーム
get_html_translation_table — 変換可能な HTML エンティティを返します
hebrev — ヘブライ語でエンコードされた文字列をビジュアル テキストに変換します
hebrevc — ヘブライ語でエンコードされた文字列をビジュアル テキストに変換します
html_entity_decode — htmlentities () 関数の逆、変換HTML エンティティを文字に変換する
htmlentities — 文字列内の一部の文字を HTML エンティティに変換する
htmlspecialchars_decode — htmlspecialchars() 関数の逆関数、HTML エンティティを文字に変換する
htmlspecialchars — 文字列内の一部の文字を HTML エンティティに変換する
implode —特定の区切り文字を使用して配列を文字列に変換します
join — 配列を implode() 関数のエイリアスである文字列に変換します
levenshtein — 2 つの単語の差を計算します
localeconv — 数値関連の形式定義を取得します
ltrim — 削除文字列の左側の空白または指定された文字
md5_file — MD5 アルゴリズムでファイルを暗号化します
md5 — MD5 アルゴリズムで文字列を暗号化します
metaphone — 文字列の発音規則を決定します
money_format — パラメーターに従って数値を暗号化します
フォーマットされた出力
nl_langinfo — 言語とロケール情報をクエリする
nl2br — 文字列内の改行文字「n」を「
」に置き換える
number_format — パラメーターに従ってフォーマットされた数値を出力する
ord — ASCII コードを文字に変換する
parse_str — 特定の形式の文字列を変数と値に変換します
print — 単一の値を出力するために使用します
printf — 必要に応じてデータを表示します
quoted_printable_decode — 文字列を 8 ビットのバイナリ文字列に暗号化します
quotemeta — いくつかの特定の文字をエスケープします
rtrim — 文字列の右側の空白または指定された文字を削除します。
setlocale — 数値、日付などのローカル形式を設定します。
sha1_file — ファイルは SHA1 アルゴリズムで暗号化されます
sha1 — 文字列を SHA1 で暗号化しますアルゴリズム
similar_text — 2 つの文字列を比較し、システムによって考慮された類似文字の数を返します🎜soundex — 文字列の発音規則を決定します
sprintf — 必要に応じてデータを返しますが、出力しません
sscanf — 文字列をフォーマットできます
str_ireplace — str_replace() 関数のように文字列を照合および置換しますが、大文字と小文字は区別しません
str_pad — 文字列の両側のパディング
str_repeat — 文字列の繰り返しの組み合わせ
str_replace — 文字列の一致と置換
str_rot13 — 文字列の ROT13 暗号化
str_shuffle — 文字列内の文字 ランダムな並べ替えの実行
str_split — 文字列を配列に分割文字間隔に応じて
str_word_count — 文字列内の英単語情報を取得します
strcasecmp — 大文字と小文字を区別せず、文字列のサイズを比較します
strchr — 比較を通じて文字を返します 文字列の strstr() 関数の部分エイリアス
strcmp — 文字列のサイズを比較します
strcoll — ローカル設定に従って文字列のサイズを比較します
strcspn — 連続して一致しない文字の長さの値を返します
strip_tags — 文字列 HTML および PHP コード内の文字を削除します
stripcslashes — addedcslashes() 関数のエスケープを解除して、処理された文字列をエスケープします
stripos — 最初に一致した位置を検索して返します。一致は大文字と小文字が区別されません
stripslashes — addslashes() 関数のエスケープを解除します 意味処理された文字列
stristr — の一部を返します文字列の比較、比較は大文字と小文字を区別しない
strlen — 文字列のエンコードされた長さを取得する
strnatcasecmp — 大文字と小文字を区別しない自然な並べ替えを使用して文字列のサイズを比較する
strnatcmp — 自然な並べ替えを使用して文字列を比較する
strncasecmp — 最初の N を比較する文字列の文字、大文字と小文字は区別されません
strncmp — 文字列の最初の N 文字を比較します
strpbrk — 比較して文字列の一部を返します
strpos — 最初に一致した位置を検索して返します
strrchr — 文字列の一部を返します文字列を後ろから前に比較します。
strrev — 文字列内のすべての文字を反転します。
strripos — 後ろから前に検索し、最初に一致した位置を返します。
strrpos — 後ろから前に検索します。最初に一致した位置を返します。
strspn — 文字が連続して出現する長さの値を返します。
strstr — 文字列の一部を比較して返します。
strtok — 文字列を指定された文字数で分割します。文字列を小文字に変換します
strtoupper — 文字列を大文字に変換します
strtr — 文字列を比較および置換します
substr_compare — 文字列をインターセプトした後に比較します
substr_count — 文字列内の特定の文字セグメントの出現数をカウントします
substr_replace — 一部の文字を置換します文字列内
substr — 文字列をインターセプトする
trim — 文字列の両側を削除する 空白または指定された文字を削除する
ucfirst — 指定された文字列の最初の文字を大文字に変換する
ucwords — 指定された文字列内の各英単語の最初の文字を変換する
vfprintf — 必要に応じてデータを大文字に変換します
vfprintf — 必要に応じてデータを返します
vsprintf — 必要に応じてデータを返しますが、出力しません
wordwrap — 特定の文字に従って文字列を分割します長さ



コードの仕様についてはどうですか?

インターフェイスを作成するときに統一された検証と戻り値を作成しました

不確実なニーズや後で発生する可能性のある問題に備えて、各ファイルに独自の注釈が必要であり、各クラスに独自の注釈が必要であり、各メソッドに注釈が必要です。 todo を追加する必要があります

主要なロジックはコメントに記述する必要があります

外部インターフェイスを呼び出す場合、プログラム内でハードコーディングすることはできません。後で変更しやすいように構成ファイルを別途提案する必要があります

データベース操作は、モデル内部では、データベース操作を C レイヤーで記述することはできません。

変数名は、その意味を明確に表現できなければなりません。

インターフェイスを作成する前にインターフェイスドキュメントを取得する必要があります。

プライベート メソッドは _ で追加する必要があります [重要、私は経験豊かなドライバーでもあるようです]



クラス ファイルにはすべて .class.php という接尾辞が付けられます (これは ThinkPHP によって内部的に使用されるクラス ライブラリ ファイルを指し、外部ロードを意味するものではありません) クラス ライブラリ ファイル)、キャメル ケースの名前付けを使用し、DbMysql.class.php のように最初の文字が大文字になります。

クラスの名前空間アドレスは、それが配置されているパス アドレスと一致します。たとえば、HomeControllerUserController クラスが存在するパスは Application/Home/Controller /UserController.class.php である必要があります。 Unix 系システムでは大文字と小文字が区別されるため、ファイルの名前付けと呼び出しの大文字と小文字が一致していることを確認してください (ThinkPHP は厳密にチェックします)。 Windows プラットフォームでもデバッグ モードの場合は同じです) );
クラス名はファイル名と一致します (上記の大文字と小文字を含む)。たとえば、UserController クラスのファイル名は UserController.class.php です。 InfoModel クラスのファイル名は InfoModel.class.php です。
さまざまなクラス ライブラリ クラスの命名には特定の標準があります

関数、構成ファイル、その他のクラス ライブラリ以外のファイルには、通常、.php という接尾辞が付けられます。第三者によるものは必要ありません);函数的命名使用小写字母和下划线的方式,例如 get_client_ip;

方法的命名使用驼峰法,并且首字母小写或者使用下划线“_”,例如 getUserName,_parseType,通常下划线开头的方法属于私有方法;
属性的命名使用驼峰法,并且首字母小写或者使用下划线“_”,例如 tableName、_instance,通常下划线开头的属性属于私有属性;
以双下划线“__”打头的函数或方法作为魔法方法,例如 __call 和 __autoload;

常量以大写字母和下划线命名,例如 HAS_ONE和 MANY_TO_MANY;

配置参数以大写字母和下划线命名,例如HTML_CACHE_ON;

语言变量以大写字母和下划线命名,例如MY_LANG,以下划线打头的语言变量
通常用于系统语言变量,例如 _CLASS_NOT_EXIST_;

对变量的命名没有强制的规范,可以根据团队规范来进行;

ThinkPHP的模板文件默认是以.html 为后缀(可以通过配置修改);

数据表和字段采用小写加下划线方式命名,并注意字段名不要以下划线开头,例
如 think_user 表和 user_name字段是正确写法,类似 _username 这样的数据表字段可能会被过滤。


tp底层看过没有?


1、看过框架的底层没有?
看过tp的数据库驱动相关。 关于配置数据库方面的,在配置文件配置就直接可以使用各种数据库类型,自己简单看了下,主要就是通过一个driver(驱动类)来判断当前连接类
型,然后调用对于的数据库操作类。
ps:如果是要我们自己实现的话,可以借助接口,每个数据库的操作类都需要集成一个接口,然后根据具体的配置去调用每个操作类。 就算后期我修改了数据库的类型,也不
会导致程序需要改动。

2、看过tp的cache类,和数据库类似,修改过redis的cache类,因为tp的redis操作类不支持认证。
主要就是在redis操作类添加了个认证

$this->handler  = new \Redis;
        $options[&#39;timeout&#39;] === false ?
            $this->handler->$func($options[&#39;host&#39;], $options[&#39;port&#39;]) :
            $this->handler->$func($options[&#39;host&#39;], $options[&#39;port&#39;], $options[&#39;timeout&#39;]);
            $this -> handler->auth( C(‘REDIS_AUTH_KEY’) );
ログイン後にコピー

3、看过tp的处理异常类
路径 ThinkPHP/library/Think/Think.class.php

主要使用的是php自带的错误处理相关函数

register_shutdown_function 定义PHP程序执行完成后执行的函数
set_error_handler 设置用户自定义的错误处理程序
set_exception_handler 设置自己的异常处理机制

借助 get_last_error获取最后一次报错的信息
根据报错级别可以自定义写日志
这个地方我们在做接口的时候纪录了一些错误日志,帮助我们排查一些问题。
如果要看文件加载以及调用关系可以借助 print_debug_backtrace获取文件加载的顺序

     // 注册AUTOLOAD方法
      spl_autoload_register(&#39;Think\Think::autoload&#39;);      
      // 设定错误和异常处理
      register_shutdown_function(&#39;Think\Think::fatalError&#39;);
      set_error_handler(&#39;Think\Think::appError&#39;);
      set_exception_handler(&#39;Think\Think::appException&#39;);
ログイン後にコピー

4、简单看了下tp的命名空间自动记载
框架下的核心类都包含进来了,其他的事借助 spl_register_autoload实现。

以上がPHP 面接の質問がまとめられ、共有されるの詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

関連ラベル:
ソース:php.cn
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
最新の問題
人気のチュートリアル
詳細>
最新のダウンロード
詳細>
ウェブエフェクト
公式サイト
サイト素材
フロントエンドテンプレート