1

数百のアドレスに ping を実行し、その値 (ミリ秒) を返す関数を作成しようとしています。これまでのところ、pingを実行して結果を取得するという最初のアイデアを達成しましたが、何百ものアドレスに同じコードを使用すると問題が発生し、タイムアウトするか最後のpingコマンドに到達するまでPHPページが停止します。

結果を段階的に出力するための提案が得られれば幸いです。現在のコードは次のとおりです。

<?php

// "for" loop added according to suggestion for browser compatibility (IE, FF, CHR, OPR, SFR)
for($i = 0; $i < 5000; $i++)
{
    echo ' ';
}

function GetPing($ip = NULL) {
    // Returns the client ping if no address has been passed to the function
    if(empty($ip)) {
        $ip = $_SERVER['REMOTE_ADDR'];
    }

    // Check which OS is being run by the client
    if(getenv('OS') == 'Windows_NT') {
        //echo '<b>Detected local system:</b> Windows NT/2000/XP/2003/2008/Vista/7<p>';
        $exec = exec("ping -n 1 -l 32 -i 128 " . $ip);
        return end(explode(' ', $exec));
    }
    else {
        //echo '<b>Detected local system:</b> Linux/Unix<p>';
        $exec = exec("ping -c 1 -s 32 -t 128 " . $ip);
        $array = explode('/', end(explode('=', $exec )));
        return ceil($array[1]) . 'ms';
    }
    // ob_flush and flush added according to suggestion for buffer output
    ob_flush();
    flush();
}

// Added to test 20 sequential outputs
for($count = 0; $count < 20; $count++)
    echo GetPing('8.8.8.8') . '<div>';

?>

いくつかのフィードバックの後、スクリプトにforループと ob_flush() および flush() を追加し、 php.iniで output_buffering を 0 に設定しました。これまでにテストしたほとんどのブラウザー (IE8、Firefox 12、Chrome 19、Opera 11、Safari 5) で動作するようです。現在のコードは意図したとおりに機能しているようですが、それを改善するための提案は非常に高く評価されています。

ご意見ありがとうございます。

4

2 に答える 2

1

これは単なる推測です。私は何年も前に、出力バッファリングも使用する(そしてwhile(true)ループで新しいメッセージをフェッチする)非常に不安定なチャットスクリプトを作成しました。

これを行っているときに、スクリプトが停止する(空白の画面)のと同じ問題が発生することがありました。文字が表示されるまでに時間がかかることもあり、さらにこれもブラウザ固有の問題でした。

これが、IE6とFF2で動作するようにスクリプトに追加した関連するコードスニペットです(私が言ったように、何年も前に...)

<?php
    // End output buffering
    ob_end_flush(); 

    // IE and Safari Workaround
    // They will only display the webpage if it's completely loaded or
    // at least 5000 bytes have been "printed".
    for($i=0;$i<5000;$i++)
    {
        echo ' ';
    }

    while( ... )
    {
        echo 'Message';
        ob_flush();
        flush();
    }
?>

それは私のために働いたので、多分あなたもそれを試してみることができます。(ただし、最新のブラウザーとサーバーインフラストラクチャがこれに対してどのように動作するかはわかりません)。

于 2012-05-30T10:02:43.383 に答える
0

あなたが探しているのは、非同期関数ではなく、スクリプトを徐々に実行して出力することだと思います。

スクリプトの実行時に PHP を段階的に出力する方法はありますか? を参照してください。

于 2012-05-29T22:57:24.047 に答える