0

タイム スタンプ付きのログ ファイルがあります。sed最初のタイム スタンプまたは最後のタイム スタンプが存在しない場合でも、2 つのタイム スタンプの間のテキストを検索したい。たとえば、9:30 から 9:40 の間を検索すると、9:30 も 9:40 も存在しないが、タイム スタンプが 9:30 から 9:40 の間にある場合でも、テキストが返されます。

私はsedワンライナーを使用しています:

sed -n '/7:30:/,/7:35:/p' xyz.log  

ただし、両方のタイムスタンプが存在する場合にのみデータを返します。タイム スタンプの 1 つが欠落している場合は、すべてが出力されます。時刻が 12 時間形式の場合、AM と PM の両方のデータが取得されます。

さらに、ログ ファイルごとに異なるタイム スタンプ形式を使用しているため、汎用コマンドが必要です。

次に、時刻形式の例をいくつか示します。

<Jan 27, 2013 12:57:16 AM MST>

Jan 29, 2013 8:58:12 AM 

2013-01-31 06:44:04,883

午前/午後、つまり 12 時間形式を含むものもあれば、24 時間形式を含むものもあるので、それも考慮する必要があります。

私もこれを試しましたが、うまくいきません:

sed -n -e '/^2012-07-19 18:22:48/,/2012-07-23 22:39:52/p' history.log
4

1 に答える 1

1

解析しなければならない時刻形式の深刻なメドレーがあるsedため、使用する正しいツールではありません。私は自動的に Perl にたどり着きますが、Python もそうするでしょうawk。時間形式を正規化する必要があります(日付については何も言わないので、時間部分のみを扱っていると思います)。

#!/usr/bin/env perl
use strict;
use warnings;
use constant debug => 0;

my $lo = "09:30";
my $hi = "09:40";

my $lo_tm = to_minutes($lo);
my $hi_tm = to_minutes($hi);

while (<>)
{
    print "Read: $_" if debug;
    if (m/\D\d\d?:\d\d:\d\d/)
    {
        my $tm = normalize_hhmm($_);
        print "Normalized: $tm\n" if debug;
        print $_ if ($tm >= $lo_tm && $tm<= $hi_tm);
    }
}

sub to_minutes
{
    my($val) = @_;
    my($hh, $mm) = split /:/, $val;
    if ($hh < 0 || $hh > 24 || $mm < 0 || $mm >= 60 || ($hh == 24 && $mm != 0))
    {
        print STDERR "to_minutes(): garbage = $val\n";
        return undef;
    }
    return $hh * 60 + $mm;
}

sub normalize_hhmm
{
    my($line) = @_;
    my($hhmm, $ampm) = $line =~ m/\D(\d\d?:\d\d):\d\d\s*(AM|PM|am|pm)?/;
    my $tm = to_minutes($hhmm);
    if (defined $ampm)
    {
        if ($ampm =~ /(am|AM)/)
        {
            $tm -= 12 * 60 if ($tm >= 12 * 60);
        }
        else
        {
            $tm += 12 * 60 if ($tm < 12 * 60);
        }
    }
    return $tm;
}

サンプルデータを使用しました:

<Jan 27, 2013 12:57:16 AM MST>

Jan 29, 2013 8:58:12 AM 

2013-01-31 06:44:04,883

Feb 2 00:00:00 AM
Feb 2 00:59:00 AM
Feb 2 01:00:00 AM
Feb 2 01:00:00 PM
Feb 2 11:00:00 AM
Feb 2 11:00:00 PM
Feb 2 11:59:00 AM
Feb 2 11:59:00 PM
Feb 2 12:00:00 AM
Feb 2 12:00:00 PM
Feb 2 12:59:00 AM
Feb 2 12:59:00 PM

Feb 2 00:00:00
Feb 2 00:59:00
Feb 2 01:00:00
Feb 2 11:59:59
Feb 2 12:00:00
Feb 2 12:59:59
Feb 2 13:00:00
Feb 2 09:31:00
Feb 2 09:35:23
Feb 2 09:36:23
Feb 2 09:37:23
Feb 2 09:35:00
Feb 2 09:40:00
Feb 2 09:40:59
Feb 2 09:41:00
Feb 2 23:00:00 
Feb 2 23:59:00
Feb 2 24:00:00
Feb 3 09:30:00
Feb 3 09:40:00

そして、それは私が正しい出力と考えるものを生成しました:

Feb 2 09:31:00
Feb 2 09:35:23
Feb 2 09:36:23
Feb 2 09:37:23
Feb 2 09:35:00
Feb 2 09:40:00
Feb 2 09:40:59
Feb 3 09:30:00
Feb 3 09:40:00

これが処理を行う唯一の方法ではないと確信しています。しかし、それはうまくいくようです。


日付分析を行う必要がある場合は、CPANの日付または時刻操作パッケージのいずれかを使用して問題に対処する必要があります。上記のコードは、スクリプト内の時間もハードコーディングしています。おそらくコマンド ライン引数として扱いたいと思うでしょう。これは完全に実行可能ですが、上記のスクリプトではありません。

于 2013-02-03T04:07:13.483 に答える