2016-12-13 9 views
2

大きな文章の中に一連のフレーズがあります。私はフレーズを強調したいと思いますが、最初にフレーズを圧縮したいと思います。私は、ほとんどの処理にPython 3.5とNLTKを使用しています。Pythonでサブセットを削除してフレーズのリストを折りたたみます

速い茶色のキツネは、迅速な怠惰な犬を

やフレーズ

茶色のキツネ

を跳んだ:私は文を持っている場合、例えば

、ブラウンキツネ

は、私は結果のHTMLが

The <b>quick brown fox</b> jumped over the lazy dog 

ない

The <b>quick <b>brown fox</b></b> jumped over the lazy dog 

私が他のサブセットである項目を削除し、リスト内包表記のいくつかの並べ替えを作ることができるはずのように思えるようになりたいですリスト内の項目は、私はかなりそれの周りに私の頭を包むように見えることはできません。他のエントリのサブセットを削除するためにフレーズをどのように崩壊させるかについてのアイデアはありますか?

答えて

1

用語がリストに表示されている場合:

terms = ['brown fox', 'quick brown', 'quick brown fox'] 

私は自分自身に対してtermリストをチェックして、リスト内の他の用語のサブセットであるすべての用語を収集することによって、サブセットのリストを作成します。

subsets = [] 
for x in terms: 
    for y in terms: 
     if x in y and x != y: 
      subsets.append(x) 

または使用してリスト内包:removその後、

subsets = [x for x in terms for y in terms if x in y and x != y] 

電子用語のリストから、すべての既知のサブセット:

phrases = [x for x in terms if x not in subsets] 

またはワンライナーで

(それはかなり読めないですので、多分お勧めしません):

phrases = [z for z in terms if z not in [x for x in terms for y in terms if x in y and x != y]] 

はあなたを与える必要があります。

>>> print(phrases) 
['quick brown fox'] 
+0

ありがとうKevin。ステートメントのための二重のトリックは理にかなっています。私は同じ減算演算子を使用して自分のコードに似たような答えを使用しました:フレーズ - = [yについてのxの点でxのxとyのxの場合はx!= y] – David

1

私は、同じ方法で独自のパーサを書くのが最善の方法だと思います。この方法では、追加のタグを削除するのではなく、挿入することはまったくありません。文中の文字を1つずつスキャンし、フレーズの文字と一致させることができます。一致するものがあれば、適切な場所にタグを挿入します。

また、長さの大きい順にフレーズを配置しました。ネストされたタグは自動的に回避されます。一致するとすぐに、フレーズはチェックされません。ここで

は私のパーサーです:

#sentence is a string 
#phrases are considered as list 
def highlightphrases(sentence, phrases): 
    phrases.sort(key=len, reverse=True) 
    sentenceCharIndex = 0 
    while sentenceCharIndex < len(sentence): 
     for phrase in phrases: 
      phraseCharIndex = 0 
      while phraseCharIndex < len(phrase) and \ 
        sentenceCharIndex + phraseCharIndex < len(sentence) and \ 
        phrase[phraseCharIndex] == sentence[sentenceCharIndex + phraseCharIndex]: 
       phraseCharIndex += 1 
      if(phraseCharIndex == len(phrase)): 
       sentence = sentence[:sentenceCharIndex+phraseCharIndex] +\ 
          "</b>" + sentence[sentenceCharIndex+phraseCharIndex:] 
       sentence = sentence[:sentenceCharIndex] +\ 
          "<b>" + sentence[sentenceCharIndex:] 
       sentenceCharIndex += phraseCharIndex + 6 
       break; 
     sentenceCharIndex+=1 
    return sentence 

注:私は基本的にPythonプログラマはないですので、コードはみすぼらしいであれば、答えの構文を向上させることができるなら、私に知らせて気にしないでくださいとにかく。編集を提案してください。私は、Pythonにはまだ新しい方法を学んで、提案はいつも歓迎です:)

+0

提案:ループすることができます(Python-speak:文字列とそのインデックスの文字に対して、 'for i、char in enumerate(string)'のように)繰り返します。それは既にここでボイラープレートの多くを取り除くはずです。 – lenz

+0

@lenz私はいくつかのインデックスをスキップしたいので、実際に使っていました。(コードを編集して、あなたのコメントの後に思いついたものを思い出しました:P) 例:The ** quick brown fox ** jump怠惰な犬の上に。その後、私はキャラクター** 'u' **ではなく、ちょうどキツネから次の比較を開始したいと思います。 forを使用して同じ目的を達成する方法はありますか? –

+0

ループ本体の先頭にチェックを入れ、チェックが失敗した場合は 'continue'ステートメントで繰り返しをスキップできます。 – lenz

関連する問題