Как с помощью команды tr заменить: точки, восклицательные и вопросительные знаки, за которыми следует пробел, на новые строки?

Я сейчас в основном взял гигантскую кувалду, решив проблему, написав сценарий.

Сначала установите интерфейс командной строки PHP, например через

sudo apt install php-cli

Я предполагаю, что PHP 7 установлен. Если вы используете PHP 5, удалите : int из заголовка метода defineTimeUntilBackup () .

Затем сохраните следующий сценарий, который я написал (который поставляется без абсолютно никаких гарантий и не протестирован, но у меня хорошее предчувствие, что он был только слегка пьян, когда писал его (прямо перед отправкой этого ответа)) в файл :

#!/usr/bin/php
<?php
// CONFIGURATION
/**
* The command to execute to create a backup.
*/
define('backupCommand', 'nice -n 19 deja-dup --backup');

/**
* The minumem period of time between 2 backups in seconds.
*/
define('minimumBackupSeparation', 20*3600);

/**
* The minimum time between 2 checks of whether a backup should be created in
* seconds. Only positive integers are permitted.
*/
define('minimumWaitingTime', 300);

/**
* The path of the file in which the time stamp of the lasted back is stored.
*/
define('latestBackupTimestampFile', 'latestBackupTimestamp');
// END OF CONFIGURATION


// Checking for root.
if(posix_getuid() == 0) {
    die('Backup script runs as root. This is probably a bad idea. Aborting.'."\n");
}

if(minimumWaitingTime !== (int) minimumWaitingTime) {
    die('Configuration error: Minumem waiting time must be an int!'."\n");
}

if(minimumWaitingTime < 1) {
    die('Configuration error: Minimum waiting time too small!'."\n");
}


while(true) {
    $timeUntilNextBackup = determineTimeUntilBackup();

    if($timeUntilNextBackup === 0) {
        createBackup();
        continue;
    }

    if($timeUntilNextBackup < 0) {
        $timeUntilNextBackup = minimumWaitingTime;
    }

    sleep($timeUntilNextBackup);
}


/**
* Returns a non-negative int when waiting for a point in time, a negative int
* otherwise. If a backups should have been created at a point in the past,
* `0` is returned.
*/
function determineTimeUntilBackup() : int {
    $latestBackup = 0;

    if(file_exists(latestBackupTimestampFile)) {
        $fileContents = file_get_contents(latestBackupTimestampFile);
        if($fileContents != (int) $fileContents) {
            die('Error: The latest backup timestamp file unexpectedly doesn\'t '
                    .'contain a timestamp.'."\n");
        }

        $latestBackup = (int) $fileContents;
    }

    $idealTimeUntilNextBackup = $latestBackup + minimumBackupSeparation - time();
    if($idealTimeUntilNextBackup < 0) {
        $idealTimeUntilNextBackup = 0;
    }

    $batteryStateReading = exec("upower -i `upower -e | grep 'BAT'` | grep 'state'");
    if(empty($batteryStateReading)) {
        echo 'Unable to read battery state!'."\n";
    } else {        
        if(strpos($batteryStateReading, 'discharging') !== false) {
            // Not connected to power.
            return -1;
        }
    }

    return $idealTimeUntilNextBackup;
}


/**
* Creates a backup and notes it in the latest backup timestamp file.
*/
function createBackup() {
    file_put_contents(latestBackupTimestampFile, time());
    exec(backupCommand);
}

Сделайте файл исполняемым, например via:

chmod 755 backup.php

Затем добавьте файл в запускаемые приложения.Как это делается, зависит от вашего дистрибутива. Для Ubuntu откройте «Автозагрузку приложений» с тире и создайте новую запись. В качестве команды просто введите путь к файлу, который вы создали выше.

Я не добавлял поддержку ограничения на время суток, поскольку мои личные обстоятельства, требующие этого, больше не существуют, но это можно легко добавить.


Редактировать: Я заметил, что батарея постоянно разряжается, если мой ноутбук был подключен к источнику питания в течение нескольких дней, в результате чего скрипт не создавал резервных копий, пока я не отключил свой ноутбук от питания на несколько минут и не подключил его повторно. .

Чтобы решить эту проблему, теперь он не считывает, сообщает ли батарея о зарядке или разрядке, а вместо этого считывает состояние адаптера питания:

#!/usr/bin/php
<?php
// CONFIGURATION
/**
* The command to execute to create a backup.
*/
define('backupCommand', 'nice -n 19 deja-dup --backup');

/**
* The minumem period of time between 2 backups in seconds.
*/
define('minimumBackupSeparation', 20*3600);

/**
* The minimum time between 2 checks of whether a backup should be created in
* seconds. Only positive integers are permitted.
*/
define('minimumWaitingTime', 300);

/**
* The path of the file in which the time stamp of the lasted back is stored.
*/
define('latestBackupTimestampFile', 'latestBackupTimestamp');
// END OF CONFIGURATION


// Checking for root.
if(posix_getuid() == 0) {
    die('Backup script runs as root. This is probably a bad idea. Aborting.'."\n");
}

if(minimumWaitingTime !== (int) minimumWaitingTime) {
    die('Configuration error: Minumem waiting time must be an int!'."\n");
}

if(minimumWaitingTime < 1) {
    die('Configuration error: Minimum waiting time too small!'."\n");
}

// Don't back up within 5 minutes after bootup.
sleep(5*60);

while(true) {
    $timeUntilNextBackup = determineTimeUntilBackup();
    echo $timeUntilNextBackup."\n";

    if($timeUntilNextBackup === 0) {
        createBackup();
        continue;
    }

    if($timeUntilNextBackup < 0) {
        $timeUntilNextBackup = minimumWaitingTime;
    }

    sleep($timeUntilNextBackup);
}


/**
* Returns a non-negative int when waiting for a point in time, a negative int
* otherwise. If a backups should have been created at a point in the past,
* `0` is returned.
*/
function determineTimeUntilBackup() : int {
    $latestBackup = 0;

    if(file_exists(latestBackupTimestampFile)) {
        $fileContents = file_get_contents(latestBackupTimestampFile);
        if($fileContents != (int) $fileContents) {
            die('Error: The latest backup timestamp file unexpectedly doesn\'t '
                    .'contain a timestamp.'."\n");
        }

        $latestBackup = (int) $fileContents;
    }

    $idealTimeUntilNextBackup = $latestBackup + minimumBackupSeparation - time();
    if($idealTimeUntilNextBackup < 0) {
        $idealTimeUntilNextBackup = 0;
    }

    $batteryStateReading = exec("acpi -a");
        if(strpos($batteryStateReading, 'on-line') === false) {
            // Not connected to power.
            return -1;
        }


    return $idealTimeUntilNextBackup;
}


/**
* Creates a backup and notes it in the latest backup timestamp file.
*/
function createBackup() {
    file_put_contents(latestBackupTimestampFile, time());
    exec(backupCommand);
}

Однако вам потребуется acpi :

sudo apt install acpi
6
03.01.2017, 14:25
3 ответа

Насколько мне известно, tr работает только с одиночными символами, а «.» - это строка, а не символ, поэтому можно делать то, что вы хотите, используя sed или awk , например:

sed -e "s/\. /\n/g" file.txt > out.txt
6
27.01.2020, 20:21

Не знаете. tr не предназначен для этого. Он предназначен для транслитерации набора отдельных символов в другой набор отдельных символов , например, A – Z в a – z . Использование tr с .␣ (точка и пробел) и \ n заменит все точки и пробелы на новые строки.

Используйте вместо этого (GNU) sed :

$ echo 'I am happy. I am here. How are you, Meg?' | sed 's/\([!.?]\) /\1\n/g'
I am happy.      
I am here.       
How are you, Meg?

Сценарий редактирования sed здесь заменит все вхождения ! , . или ? , за которыми следует пробел, тот же символ и новая строка.

13
27.01.2020, 20:21

Как уже упоминалось, вы не можете достичь желаемого с помощью tr из-за природы tr . Но есть много других альтернатив. Например, Python 2.

В качестве однострочника мы могли бы сделать это:

python -c "import sys;print '\n'.join([ j.strip() for l in sys.stdin.readlines() for j in  l.rstrip().split('.')])" < input.txt

В качестве сценария это будет примерно так:

#!/usr/bin/env python
import sys

sentences = []
for line in sys.stdin:
    for sentence in line.rstrip().split('.'):
        sentences.append(sentence.strip())

print "\n".join(sentences)

И используется так:

$ ./split_to_lines.py  < input.txt                                                                    
I am happy
I am here
How are you, Meg?

Здесь не происходит ничего особенно сложного - мы просто разбиваем все строки в файле на предложения по адресу . , а затем удалите начальные и конечные пробелы для каждого предложения. Все, что попадает в список, который затем собирается с помощью функции .join () .

0
27.01.2020, 20:21

Теги

Похожие вопросы