how to replace a string in a stream for very large files

283 views Asked by At

How can I replace a string in a file that cannot be fully loaded into memory
I can read it a few byes at a time, but how can I be sure I didn't read into the middle of my phrase?
I think I should save the last strlen(phrase) length of bytes and try to replace last+current
This is my WIP

function stream_str_replace(string $search, string $replace, $handle, int $length, &$count = null)
{
    // assure $handle is a resource
    if (!is_resource($handle)) {
        throw new UnexpectedValueException('handle must be a valid stream resource');
    }

    // assure $handle is a stream resource
    if ($resourceType = get_resource_type($handle) !== 'stream') {
        throw new UnexpectedValueException('handle must be a valid stream resource, but is a "' . $resourceType . '"');
    }

    $sLength = strlen($search);

    $lastInSLength = '';
    while (!feof($handle)) {
        $str = fread($handle, $length - $sLength - 1);

        $batchCount = 0;
        $res = str_replace($search, $replace, $lastInSLength . $str, $batchCount);

        if ($batchCount) {
            $count += $batchCount;
            fseek($handle, -($length - 1));
            fwrite($handle, $res); // this does not seem to work as I intend it to
        }

        $lastInSLength = substr($str, -$sLength);
    }
}

$fh = fopen('sample.txt', 'r+');

stream_str_replace('consectetur', 'foo', $fh, 50, $count);

fclose($fh);
0

There are 0 answers