web-dev-qa-db-ja.com

Pythonでは、特定の文字列を含む行を印刷するのではなく、特定の文字列を含まない行を印刷するにはどうすればよいですか。

非常に大きなログファイルを圧縮しようとしています。これを行うには、文字列「StatusRequest」と「StatusResponse」を含むすべての行を削除し、他の行をこの文字列なしで印刷する必要があります。ここまでのコードは次のとおりです(コマンドプロンプトから実行するため)。

   if (sys.argv[1])=="--help":
       print ("\n")
       print ("Argument 1: Enter name of '.py' file")
       print ("-i or --input: name of Catalina log")
       print ("-o or --output: file to output to")
       print ("\n")
   if (sys.argv[1])=="-h":
       print ("\n")
       print ("Argument 1: Enter name of '.py' file")
       print ("-i or --input: name of Catalina log")
       print ("-o or --output: file to output to")
       print ("\n")

   else:
       print 'Number of arguments:', len(sys.argv), 'arguments.'
       print 'Argument List:', str(sys.argv)

       Numarg = (len(sys.argv))
       i=1
       while i<=(Numarg-4):
           search1="StatusRequest"
           search2="StatusResponse"
           if (sys.argv[Numarg-2])=="-o":
               outputfile=sys.argv[Numarg-1]

           if (sys.argv[Numarg-2])=="--output":
               outputfile=sys.argv[Numarg-1]

           if (sys.argv[i])=="-i":
               filename=(sys.argv[i+1])

               log=(filename)
               print ("You entered the log: " + log)

               f=open(log, 'r')
               read_data = f.read()
               f.close

               f=open(log, 'r')
               readlines_data=f.readlines()
               f.close()
               i=i+1
           if (sys.argv[i])=="--input":
               filename=(sys.argv[i+1])
               log=(filename)
               print ("You entered the log: " + log)

               f=open(log, 'r')
               read_data = f.read()
               f.close

               f=open(log, 'r')
               readlines_data=f.readlines()
               f.close()
               i=i+1
           for line in readlines_data:
               if not ("StatusRequest" or "StatusResponse") in line:
                   result=line
                   print (line)
       f=open(outputfile, 'a')
       f.write(result + "\n")
       f.close()

スクリプトの最後に集中して、私の質問に答えることができます。本当に...とにかく、なぜこれが機能しないのかわかりません...すべての行を出力しています。そして、私はすでにnotの場所を切り替えてみたので、慣用的にもっと理にかなっていますが、コードでは何も変更されませんでした。どんな助けでも大歓迎です:)

9
user3877194

問題はnotの使用ではありません。orは、それが何をしていると思っているのかを意味しません(そして、もしあなたがそれを熟考したとしてもできませんでした =):

if not ("StatusRequest" or "StatusResponse") in line:

("StatusRequest" or "StatusResponse")lineに現れるかどうかを尋ねています。しかし、その式は"StatusRequest"とまったく同じです。

英語で書いてください。「どちらも揃っていない場合」と言っているわけではありません。 Pythonにはneither/none関数はありませんが、any関数はありますので、これを行うことができます:

if not any(value in line for value in ("StatusRequest", "StatusResponse")):

これは英語ほどよくありません。英語では「値 'StatusRequest'と 'StatusResponse'のいずれも並んでいない場合」と言うことができますが、Pythonでは「値 'StatusRequest'の場合、値が並んでいない場合は 'StatusRequest'と言う必要があります。および「StatusResponse」」。

または、この場合はもっと単純に:

if "StatusRequest" not in line and "StatusResponse" not in line:

(また、inを使用して全体を否定する代わりに、not inを使用できることに注意してください。)

16
abarnert

この行を置き換えます:

if not ("StatusRequest" or "StatusResponse") in line:

これで:

if "StatusRequest" not in line and "StatusResponse" not in line:

超エレガントではありませんが、それでうまくいきます。 2つの文字列を同じ行と比較するより速い方法があるかどうかはわかりません。

3
TheSoundDefense

notを使用すると、最初に持っていたように、括弧内の式を否定できます。あなたはそれが否定しているものを修正する必要があるだけです、それは文字列がline内にあるということです:

if not ("StatusRequest" in line or "StatusResponse" in line):

1
stever

各条件を個別に配置する必要があります。

for line in readlines_data:
    if ("StatusRequest" not in line) and "(StatusResponse" not in line):
        result = line
        print(line)
1
Christian