我正在尝试在s3的两个日期之间获取所有文件-
aws s3 ls 's3://big-data-analytics-prod/LZ/copycat/emailstats/' --recursive | sed "/2018-06-01/,/`date +%Y-%m-%d -d '30 days ago'`/p"
它倾向于给我所有数据。使用了此功能,但不起作用-https://stackoverflow.com/a/29412898/2251058(不过滤任何内容) 这是正确的方法吗?
对此有任何帮助。
更新
根据要求-RavinderSingh13
我使用-n作为,发现没有-n时,sed命令充当cat命令。
按照jhnc的建议,我添加了-n用作grep命令,它给了我空的结果
样本输入模式如下所示,结果为空
2018-06-01 13:32:20 <filesize> <filepath>....gz
.
.
.
.
2019-02-04 00:13:12 12344 <filepath>....gz
添加了-n(用作grep)后,我在上面的一个错误中未使用-n,但未显示任何输出。为了检查,我使用了以下命令。它没有输出。
echo "2018-01-01" | sed -n "/2018-06-01/,/`date +%Y-%m-%d -d '30 days ago'`/p"
echo "2019-01-01" | sed -n "/2018-06-01/,/`date +%Y-%m-%d -d '30 days ago'`/p"
echo "2019-02-01" | sed -n "/2018-06-01/,/`date +%Y-%m-%d -d '30 days ago'`/p"
echo "2019-02-01" | sed -n "/2018-06-01/,/2019-01-05/p"
echo "2019-06-30" | sed -n "/2018-06-01/,/2019-01-05/p"
答案 0 :(得分:1)
问题中给出的sed
代码仅在开始日期出现在列表中时才能正常工作。
我们需要进行字符串比较,而不是进行正则表达式匹配。 awk或perl都能胜任。
花哨的perl:
#!/usr/bin/perl
# Usage: $0 date1 date2
# where dates can be anything supported by date(1)
# remember to "quote whitespace"
# fancy date parsing
open(my $cmd, '-|', 'date', '+%Y-%m-%d %H:%M:%S', '--date', $ARGV[0]||'1970-01-01') or die $!;
my $start = <$cmd>;
chomp $start;
close $cmd;
open(my $cmd, '-|', 'date', '+%Y-%m-%d %H:%M:%S', '--date', $ARGV[1]||'now') or die $!;
my $end = <$cmd>;
chomp $end;
close $cmd;
# start should be earlier than end
($start, $end) = ($end, $start) if $start gt $end;
while (<STDIN>) {
print if $_ ge $start && $_ le $end;
}
简单的awk(可以使用与原始sed相同的方式嵌入通话日期):
awk '$0>="2018-06-01" && $0<="2019-01-01" {print}'
答案 1 :(得分:1)
作为一种简单(不包含sed)的解决方案,请尝试以下操作:
input.txt
示例文件2018-06-01 13:32:20 <filesize> <filepath>....gz
2019-01-01 01:23:45 <filesize> <filepath>....gz
2019-01-30 00:22:45 <filesize> <filepath>....gz
2019-02-01 11:03:05 <filesize> <filepath>....gz
2019-02-02 02:24:55 <filesize> <filepath>....gz
2019-02-04 00:13:12 12344 <filepath>....gz
如下所示:
$ ./thisscript 2019-01-01 2019-02-02
然后使用以下命令调用脚本:
2019-01-01 01:23:45 <filesize> <filepath>....gz
2019-01-30 00:22:45 <filesize> <filepath>....gz
2019-02-01 11:03:05 <filesize> <filepath>....gz
2019-02-02 02:24:55 <filesize> <filepath>....gz
产量:
aws
如果您希望直接处理#!/bin/bash
# usage: thiscommand startdate enddate
# starddate and enddate should be in the format: yyyy-mm-dd
start=${1//-/}
end=${2//-/}
while read -r date rest; do
date2=${date//-/}
if ((start <= date2 && date2 <= end)); then
echo "$date $rest"
fi
done < <(aws s3 ls 's3://big-data-analytics-prod/LZ/copycat/emailstats/' --recursive)
命令的输出,可以说:
#include <stdio.h>
int main(){
int i;
char arr1[10]={'0','1','2','3','4','5','6','7','8','9'};
char arr2[10]="0123456789";
for(i=0 ; i<11 ;++i){
printf("arr1[%d] is %c \t\t",i,arr1[i]);
printf("arr2[%d] is %c\n",i,arr2[i]);
if(arr1[i]=='\0')
printf("%d . character is \\0 of arr1 \n",i);
if(arr2[i]=='\0')
printf("%d . character is \\0 of arr2 \n",i);
}
return(0);
}
您会发现没有窍门:它只是将日期格式转换为正数并进行算术比较。
答案 2 :(得分:0)
与此同时,我学到了一些awk,而是使用awk进行了计算,但忘了分享作为答案。
endtime=`date +%Y-%m-%d -d '-30 day'`
begintime="2018-06-01"
bucket="s3://big-data-analytics-prod/"
path='s3://big-data-analytics-prod/LZ/copycat/emailstats/'
aws s3 ls path --recursive | awk '{if($1>=$begintime && $1<=$endtime) {print $4} }'
一行中的
aws s3 ls 's3://big-data-analytics-prod/LZ/copycat/emailstats/' --recursive | awk -v begintime="2018-06-01" -v endtime="`date +%Y-%m-%d -d '30 days ago'`" '{if($1>=begintime && $1<=endtime) {print $4}}'