【问题标题】:How to find lines using patterns in a file in UNIX如何在 UNIX 中使用文件中的模式查找行
【发布时间】:2014-11-27 05:56:20
【问题描述】:

我正在尝试使用包含大约 5000 个模式(以一行分隔)的 .txt 文件来搜索另一个包含 18000 行的文件以查找任何匹配项。到目前为止,我已经尝试了所有在互联网上可以找到的 grep 和 awk 形式,但仍然无法正常工作,所以我完全被难住了。

这是每个文件中的一些文本。

图案.txt

rs2622590
rs925489
rs2798334
rs6801957
rs6801957
rs13137008
rs3807989
rs10850409
rs2798269
rs549182

没有多余的空格或任何东西。

文件.txt

snpid hg18chr bp a1 a2 zscore pval CEUmaf
rs3131972       1       742584  A       G       0.289   0.7726  .
rs3131969       1       744045  A       G       0.393   0.6946  .
rs3131967       1       744197  T       C       0.443   0.658   .
rs1048488       1       750775  T       C       -0.289  0.7726  .
rs12562034      1       758311  A       G       -1.552  0.1207  0.09167
rs4040617       1       769185  A       G       -0.414  0.6786  0.875
rs4970383       1       828418  A       C       0.214   0.8303  .
rs4475691       1       836671  T       C       -0.604  0.5461  .
rs1806509       1       843817  A       C       -0.262  0.7933  .

file.txt 是直接从 med 目录下载的。

我对 UNIX 很陌生,所以任何帮助都会很棒!

抱歉编辑:我确实尝试了你们推荐的每一件事,但结果是空白的。我是否可能在我的文本文件中遗漏了语法问题或其他内容?

P.P.S 我知道有一些匹配作为单独的 greps 工作。我将把这个问题移到 unix.stackexchange。谢谢你们的回答,我会全力以赴的。

问题已解决:我显然使用的是 DOS 回车。我之前不知道这个,所以谢谢大家回答。对于遇到此问题的未来用户,以下是有效的解决方案:

dos2unix *

awk 'NR==FNR{p[$0];next} $1 in p' Patterns.txt File.txt > Output.txt

【问题讨论】:

  • Google “文件中的 grep 模式”返回了大量答案。但显然“所有形式的 grep”不包括 grep -f : unix.stackexchange.com/questions/83260/…
  • 更适合 unix.stackexchange.com
  • 如果您的模式文件包含 DOS 回车符(而目标文件显然没有,至少在相同的地方),则不会有匹配项。搜索数百个(或可能数千个)答案为dos2unix 的问题。 bash tag wiki 也有讨论。
  • 不要使用pattern这个词,因为它有歧义。您的文件包含字符串。你想用它们来做字符串或正则表达式比较或其他什么吗?如果正则表达式你想要 BREs 或 EREs 还是别的什么?你想要部分匹配还是完整匹配?您要匹配特定字段还是整行或其他内容?
  • @John3136 为什么你会建议这更适合不同的论坛?这是一个微不足道的文本操作问题,我们只需要 OP 提供更多关于问题所在的信息,然后我们就可以帮助他们解决它。

标签: regex unix awk grep


【解决方案1】:

你可以在这里使用grep -Fw

grep -Fw -f Pattern.txt File.txt

使用的选项有:

  • -F - 修复了将字符串搜索作为非正则表达式输入的问题
  • -w - 仅匹配完整的单词
  • -f file - 从文件中读取模式

【讨论】:

  • 没关系,但是当它们似乎只想匹配第一个字段时,它们会匹配 File.txt 每一行的任何部分,因此有可能会产生错误匹配。
  • 同意,我会使用 awk one 衬垫来匹配第一个字段,尽管正在等待 OP 留下一些 cmets 来澄清。
【解决方案2】:

idk 是不是你想要的,但这会打印 File.txt 中第一个字段等于 Patterns.txt 中的字符串的每一行:

awk 'NR==FNR{p[$0];next} $1 in p' Patterns.txt File.txt

如果这不是您想要的,请告诉我们您想要什么。如果它是您想要的,但没有产生您期望的输出,那么您的一个或两个文件包含在 Windows 中创建的控制字符,因此请先在它们上运行 dos2unix 或类似的。

【讨论】:

  • 感谢 Ed,工作完美。我在每个文件上运行了 dos2unix 并运行了你的 awks 代码。想出了所有匹配项,我现在将其通过管道传输到另一个文件中。 dos2unix * awk 'NR==FNR{p[$0];next} $1 in p' Patterns.txt File.txt |输出.txt
【解决方案3】:

使用 shell 脚本读取包含您的模式的文件的每一行,然后对其进行 fgrep。

#!/bin/bash

FILENAME=$1

awk '{kount++;print   $0}' $FILENAME | fgrep -f - PATTERNFILE.txt

【讨论】:

  • 您认为您的 awk 脚本在做什么而 cat $FILENAME 不会做?管道的意义何在?
猜你喜欢
  • 2013-12-10
  • 1970-01-01
  • 1970-01-01
  • 2013-02-09
  • 2011-12-26
  • 2018-09-22
  • 1970-01-01
  • 2017-02-14
  • 1970-01-01
相关资源
最近更新 更多