我有 2 个包含以下数据的文件:
文件1
22:50:48] Return_M
22:50:49] Return_A
22:50:50] Return_F
22:50:51] Return_K
22:50:52] Return_Y
文件2
22:50:48] <0> X led_required
22:50:48] <0> X start_rules
22:50:48] <0> X leadstart
22:50:49] <0> X asynchronous_start
22:50:49] <0> X controldown
22:50:49] <0> X select_set(3)
22:50:49] <0> X limiting_rules
22:50:50] <0> X stock_manager
22:50:50] <0> X led_blink
22:50:50] <0> X start_required
22:50:51] <0> X control_down
22:50:51] <0> X select_set(3)
22:50:51] <0> X start_rules
22:50:52] <0> X stock_manager
22:50:52] <0> X blink_led
我想要一个输出以下内容的文件:
22:50:48] Return_M <0> X led_required
22:50:48] Return_M <0> X start_rules
22:50:48] Return_M <0> X leadstart
22:50:49] Return_A <0> X asynchronous_start
22:50:49] Return_A <0> X controldown
22:50:49] Return_A <0> X select_set(3)
22:50:49] Return_A <0> X limiting_rules
22:50:50] Return_F <0> X stock_manager
22:50:50] Return_F <0> X led_blink
22:50:50] Return_F <0> X start_required
22:50:51] Return_K <0> X control_down
22:50:51] Return_K <0> X select_set(3)
22:50:51] Return_K <0> X start_rules
22:50:52] Return_Y <0> X stock_manager
22:50:52] Return_Y <0> X blink_led
它基本上将文件 1 的返回代码放入文件 2 中,但仅在匹配的时间。
答案1
我已经包含了两个(略有不同)脚本,它们应该可以完成您想要的操作:Python 脚本和 Bash 脚本。
Python解决方案
#!/usr/bin/env python3
# -*- encoding: utf-8 -*-
"""prefix_join.py"""
import sys
input_1 = sys.argv[1]
input_2 = sys.argv[2]
# Initialize a list to store prefixes as they occur
prefix_list = list()
# Parse the first input file
data_1 = dict()
with open(input_1, "r") as file_1:
for line in file_1:
# Remove trailing and leading whitespace
line = line.strip()
# Split the string on the first whitespace character
prefix, sep, suffix = line.partition(" ")
# Add the prefix the list of prefixes
if prefix not in prefix_list:
prefix_list.append(prefix)
# Add the prefix to the first data dictionary
if prefix not in data_1:
data_1[prefix] = list()
# Add the suffix to the data dictionary
data_1[prefix].append(suffix)
# Parse the second input file
data_2 = dict()
with open(input_2, "r") as file_2:
for line in file_2:
# Remove trailing and leading whitespace
line = line.strip()
# Split the string on the first whitespace character
prefix, sep, suffix = line.partition(" ")
# Add the prefix the list of prefixes
if prefix not in prefix_list:
prefix_list.append(prefix)
# Add the prefix to the first data dictionary
if prefix not in data_2:
data_2[prefix] = list()
# Add the suffix to the data dictionary
data_2[prefix].append(suffix)
# Output the joined data
for prefix in prefix_list:
for value_1 in data_1.get(prefix, list()):
for value_2 in data_2.get(prefix, list()):
output_line = "{} {} X {}".format(prefix, value_1, value_2)
print(output_line)
你可以像这样运行它:
python prefix_join.py file-1.txt file-2.txt
在您的示例数据上,它会产生以下输出:
22:50:48] Return_M X <0> X led_required
22:50:48] Return_M X <0> X start_rules
22:50:48] Return_M X <0> X leadstart
22:50:49] Return_A X <0> X asynchronous_start
22:50:49] Return_A X <0> X controldown
22:50:49] Return_A X <0> X select_set(3)
22:50:49] Return_A X <0> X limiting_rules
22:50:50] Return_F X <0> X stock_manager
22:50:50] Return_F X <0> X led_blink
22:50:50] Return_F X <0> X start_required
22:50:51] Return_K X <0> X control_down
22:50:51] Return_K X <0> X select_set(3)
22:50:51] Return_K X <0> X start_rules
22:50:52] Return_Y X <0> X stock_manager
22:50:52] Return_Y X <0> X blink_led
重击解决方案
#!/usr/bin/env bash
# prefix-join.sh
# Get the input files as command-line arguments
input_file_1="$1"
input_file_2="$2"
# Set the internal field separator to be a newline (don't include spaces or tabs)
IFS=$'\n'
# Iterate over the lines of the first input file
for line_1 in $(cat "${input_file_1}"); do
# Split the line on the first space
prefix_1="${line_1/ */}";
suffix_1="${line_1#*] }";
# Iterate over the lines of the second input file
for line_2 in $(cat "${input_file_2}"); do
# Split the line on the first space
prefix_2="${line_2/ */}";
suffix_2="${line_2#*] }";
# If the prefixes agree, combine the suffixes and output the result
if [[ "${prefix_1}" = "${prefix_2}" ]]; then
echo "${prefix_1} ${suffix_1} X ${suffix_2}"
fi
done
done
你可以像这样运行它:
bash prefix-join.sh file-1.txt file-2.txt
对于示例数据,这会产生与 Python 脚本相同的输出。
答案2
我通过以下命令完成
命令
for ((i=1;i<=5;i++)); do j=`awk -v i="$i" 'NR==i{print $1}' g1.txt`;k=`awk -v i="$i" 'NR==i{print $NF}' g1.txt`;awk -v j="$j" -v k="$k" '$1==j{print $1,k,$2,$3,$4}' g2.txt;done
输出
for ((i=1;i<=5;i++)); do j=`awk -v i="$i" 'NR==i{print $1}' g1.txt`;k=`awk -v i="$i" 'NR==i{print $NF}' g1.txt`;awk -v j="$j" -v k="$k" '$1==j{print $1,k,$2,$3,$4}' g2.txt;done
22:50:48] Return_M <0> X led_required
22:50:48] Return_M <0> X start_rules
22:50:48] Return_M <0> X leadstart
22:50:49] Return_A <0> X asynchronous_start
22:50:49] Return_A <0> X controldown
22:50:49] Return_A <0> X select_set(3)
22:50:49] Return_A <0> X limiting_rules
22:50:50] Return_F <0> X stock_manager
22:50:50] Return_F <0> X led_blink
22:50:50] Return_F <0> X start_required
22:50:51] Return_K <0> X control_down
22:50:51] Return_K <0> X select_set(3)
22:50:51] Return_K <0> X start_rules
22:50:52] Return_Y <0> X stock_manager
22:50:52] Return_Y <0> X blink_led
答案3
注意:这是重新运行我之前给你的回答(关于一个较新的问题,但我错过了这个新鲜问题)
假设这两个文件已排序,它们看起来是:
$ join file1 file2
22:50:48] Return_M <0> X led_required
22:50:48] Return_M <0> X start_rules
22:50:48] Return_M <0> X leadstart
22:50:49] Return_A <0> X asynchronous_start
22:50:49] Return_A <0> X controldown
22:50:49] Return_A <0> X select_set(3)
22:50:49] Return_A <0> X limiting_rules
22:50:50] Return_F <0> X stock_manager
22:50:50] Return_F <0> X led_blink
22:50:50] Return_F <0> X start_required
22:50:51] Return_K <0> X control_down
22:50:51] Return_K <0> X select_set(3)
22:50:51] Return_K <0> X start_rules
22:50:52] Return_Y <0> X stock_manager
22:50:52] Return_Y <0> X blink_led
这join
实用程序执行关系型 INNER JOIN 操作在它的两个输入文件上。默认情况下,第一列是连接列,输入需要在此列中进行排序。
与新问题相比,该问题的另一件事是注意列的顺序。默认情况下,join
始终首先放置连接列,然后是第一个文件中的所有列,然后是第二个文件中的所有列。
您可以使用 标志-o
来更改此顺序join
(请参阅手册)。