👌

BLASTエラーの原因となる制御文字の処理:FASTAファイル修正プログラムの実装・解説

2024/10/28に公開

制御文字とキャレット表記について

キャレット表記の基本

キャレット表記は、ASCIIコードにおける制御文字を視覚的に表現するための記法です。

  1. 表記方法
    • ^ (キャレット) + アルファベット大文字
    • 例:^A = 制御コード1(Start of Heading:ヘッダ開始)
    • ASCIIコード0-31の範囲の制御文字を表現
    • ASCIIコード一覧表
  2. 主な使用場面
    • プログラミング環境でのデバッグ(テキストエディタやプログラミング環境では、特定の制御文字を簡単に参照するためにこの表記が使われます。)
    • テキスト処理における制御文字の表現
    • 文書校正や特殊文字の確認

今回の問題との関連

FASTAファイルで見つかった^Aは、実際にはASCII制御コード1(SOH: Start of Heading)として保存されていました。これが複数のエントリーを不適切に連結する原因となっていました。

問題点

  • 複数のエントリーが"^A"で連結されていたため、BLASTが最初のエントリーのみしか認識しない
  • 解析に影響を与える可能性がある
  • 正確な結果を得るために、各エントリーを適切に分割する必要がある

解決方法

2つのPythonスクリプトを作成して問題を解決しました:

  1. create_conversion.py: 制御文字の変換を行う
  2. FASTA_entry_spliter.py: FASTAエントリーの分割を実行

create_conversion.py の主な機能

  1. 制御文字の変換関数
def to_caret_notation(s):
    """
    ASCII制御文字(0-31)をキャレット表記に変換
    例:ASCII(1) → ^A
    """
    result = []
    for char in s:
        if ord(char) < 32:  # 制御文字の範囲
            result.append('^' + chr(ord(char) + 64))
        else:
            result.append(char)
    return ''.join(result)

  1. 特殊文字の変換関数
  • caret_to_tab(): "^A" → タブに変換
  • caret_to_kaigyo(): "^J" → 改行に変換

FASTA_entry_spliter.py の主な機能

  1. エントリー分割処理
  • ヘッダー行(">"で始まる行)の検出
  • タブ区切りされたヘッダーの分割
  • シーケンスデータの適切な割り当て
create_conversion.pyのプログラム全文
def to_caret_notation(s):
    """
    文字列内の制御文字をキャレット表記に変換する関数。
    """
    result = []
    for char in s:
        if ord(char) < 32:  # ASCIIコードが0から31の範囲内
            result.append('^' + chr(ord(char) + 64))
        else:
            result.append(char)
    return ''.join(result)

def caret_to_tab(s):
    """
    文字列内のキャレット表記をタブに変換する関数。
    """
    return s.replace('^A', '\t')

def caret_to_kaigyo(s):
    """
    文字列内のキャレット表記を改行に変換する関数。
    """
    return s.replace('^J', '\n')

def convert_caret_to_tab_in_file(input_file, output_file):
    """
    テキストファイル内のキャレット表記をタブに変換する関数。
    """
    with open(input_file, 'r', encoding='utf-8') as file:
        content = file.read()
        # 制御文字をキャレット表記に変換
        caret_content = to_caret_notation(content)
        # キャレット表記をタブに変換
        tab_content = caret_to_tab(caret_content)
        # キャレット表記を改行に変換
        kaigyo_content = caret_to_kaigyo(tab_content)

    with open(output_file, 'w', encoding='utf-8') as file:
        file.write(kaigyo_content)

# テスト用のファイルパス
input_file = 'filename.fas'
output_file = 'filename2.fas'
convert_caret_to_tab_in_file(input_file, output_file)

FASTA_entry_spliter.pyのプログラム全文
import re

def split_fasta_entries(input_file, output_file):
    with open(input_file, 'r') as infile, open(output_file, 'w') as outfile:
        current_headers = []
        current_sequence = ""

        for line in infile:
            line = line.strip()

            if line.startswith('>'):
                # 新しいヘッダーが見つかった場合、前のエントリーを書き出す
                if current_headers and current_sequence:
                    for header in current_headers:
                        outfile.write(f"{header}\n{current_sequence}\n\n")

                # タブで区切られたヘッダーを処理
                headers = line.split('\t')
                current_headers = []
                for header in headers:
                    if header.startswith('>'):
                        current_headers.append(header)
                    else:
                        # '>'で始まらないヘッダーに'>'を追加
                        current_headers.append('>' + header.lstrip())

                current_sequence = ""
            else:
                # シーケンス行を追加
                current_sequence += line

        # 最後のエントリーを書き出す
        if current_headers and current_sequence:
            for header in current_headers:
                outfile.write(f"{header}\n{current_sequence}\n\n")

input_file = "filename.fas"
output_file = "filename2.fas"
split_fasta_entries(input_file, output_file)

使用例

# 入力ファイルと出力ファイルのパスを指定
input_file = 'blastFile.fas'
output_file = 'blastFile_v2.fas'

# 変換処理の実行
convert_caret_to_tab_in_file(input_file, output_file)
split_fasta_entries(output_file, final_output_file)

結果

プログラム実行前

プログラム実行後

  • 各エントリーが適切に分割された
  • BLASTでの解析が正確に行えるようになった
  • データの可読性が向上
  • 制御文字の問題が解消された

まとめ

このプログラムにより、キャレット表記で表される制御文字に起因するFASTAファイルの形式問題が解決され、より正確な解析が可能になりました。また、制御文字の適切な処理により、データの整合性と可読性も向上しました。

Discussion