2016-05-04 31 views
0

Ich habe einen Code geschrieben, der vier verschiedene Zeichenfolgen findet.Suchen von Zeichenfolgen, je nachdem, was zuerst angezeigt wird

ATG ist immer am Anfang und TAG, TGA oder TAA sind die "Stop" -Sequenzen.

Die Anzahl der Zeichen zwischen START und STOP-Sequenzen sollte um ein Vielfaches von 3.

Zum Beispiel in der folgenden String: ACC ATG CCC TAG TTT mein Programm kehrt ATG CCC TAG.

Und in dieser Zeichenfolge: nicht ein Vielfaches von drei ist, so dass es AA ATG CC TAG T TAA das Programm ATG CCTAGT TAA, da die Anzahl der Zeichen zwischen ATG und TGA zurück sucht nach der nächsten "Stop" -Sequenz, die in diesem Fall TAA ist.

Hier ist der Code:

public class TagFinder { 
    public String findProtein(String dna) { 
     String fpL = dna.toLowerCase(); 
     int start = fpL.indexOf("atg"); 
     int stop = fpL.indexOf("tag", start+3); 
     int stop2 = fpL.indexOf("tga", start+3); 
     int stop3 = fpL.indexOf("taa", start+3); 
     if (start == -1) { 
      return ""; 
     } 

     if ((stop - start) % 3 == 0) { 
      return fpL.substring(start, stop+3); 
     } 

     if ((stop2 - start) % 3 == 0) { 
      return fpL.substring(start, stop2+3); 
     } 

     if ((stop3 - start) % 3 == 0) { 
      return fpL.substring(start, stop3+3); 
     } 
     else { 
      return ""; 
     } 
    } 

jedoch im folgenden String "ATT ATG CCC TAA TAG", wird der Code zuerst ATG CCCTAA TAG, obwohl TAA finden ist die erste "Stop" -Sequenz in der Zeichenkette und die Anzahl der Zeichen zwischen ATG und TAA ist 3.

Wie kann ich dieses Programm schreiben, so dass die "STOP" -Sequenz zuerst erscheint in der Zeichenfolge und ist n3 weg von der Startsequenz zurückgegeben wird.

Vielen Dank.

Antwort

0

Reguläre Ausdrücke tun.

String input = "ACCATGCCCTAGTTT"; 
    String expected = "ATGCCCTAG"; 

    Pattern pattern = Pattern.compile("(ATG)(.{3})*?(TAG|TGA|TAA)", 
      Pattern.CASE_INSENSITIVE); 
    Matcher m = pattern.matcher(input); 
    while (m.find()) { 
     System.out.printf("[%d] %s%n", m.start(), m.group()); 
    } 

In der über der Startposition ist nicht notwendigerweise ein Vielfaches von 3. Wenn die Startposition ein Vielfaches von 3 sein muss, dann wäre es am einfachsten, Gruppen von drei Buchstaben zu machen und einen Separator.

input = input.replaceAll(".{3}", "$0,"); 

    Pattern pattern = Pattern.compile("(ATG,)(.{4})*?(TAG|TGA|TAA),", 
      Pattern.CASE_INSENSITIVE); 
    Matcher m = pattern.matcher(input); 
    while (m.find()) { 
     System.out.printf("[%d] %s%n", m.start() * 3/4, m.group().replace(",", "")); 
    } 
0

Von

if ((stop - start) % 3 == 0) { return fpL.substring(start, stop+3); }

Es findet ersten TAG und die return-Anweisung aufgerufen wird. Wenn Sie den ersten Haltepunkt wirklich finden möchten, fügen Sie eine Comaprison-Logik zwischen stop, stop2 und stop3 hinzu, um herauszufinden, welcher der kleinste Index ist. Dann die % 3 Prüfung für jeden und Rückkehr von der ersten, die in Ordnung ist, oder die ganze Zeichenfolge, wenn es keinen gültigen Fall gibt. Wie wäre es mit einem regulären Ausdruck für dieses Problem? Etwas in den Zeilen von (ATG)\w{3}(TAG|TGA|TAA).

0

Sie müssen das Minimum aller Stopp-Tags, um zu bestimmen, so dass ich so etwas schreiben würde:

[...] 
    int minStop = MAXINT; 

    if ((stop - start) % 3 == 0 && minStop > stop) { 
     minStop = stop; 
    } 

    if ((stop2 - start) % 3 == 0 && minStop > stop2) { 
     minStop = stop2; 
    } 

    if ((stop3 - start) % 3 == 0 && minStop > stop3) { 
     minStop = stop3; 
    } 

    if (minStop < MAXINT) { 
     return fpL.substring(start, minStop+3); 
    } else { 
     [...] 
    } 
0

Der folgende Code eine Liste aller Suchbegriffe verwendet, dann das Minimum angepasst Index auswählt.

public String findProtein(String dna) { 
    String fpL = dna.toLowerCase(); 
    int start = fpL.indexOf("atg"); 

    List<String> searchWords = new ArrayList<>(); 
    searchWords.add("tag"); 
    searchWords.add("tga"); 
    searchWords.add("taa"); 

    int start = fpL.indexOf("atg"); 
    try{ 
     int startIndex = searchWords.stream().mapToInt(word -> fpL.indexOf(word, 3 + start)).filter(idx -> idx >= 0 && 0 == idx % 3) 
       .min().getAsInt(); 

     return dna.substring(start, startIndex + 3); 

    } catch(NoSuchElementException ex) { 
     return ""; 
    } 
} 
0

Der Grund der Code „TAG“ zuerst findet, ist, weil die Art und Weise Sie Ihren Code geschrieben haben: Ihre erste if Anweisung prüft für „TAG“. Wenn es einen findet, gibt es die Zeichenfolge zwischen "ATG" und "TAG" zurück und wird beendet.

Was Sie tun müssen, ist eine min Variable zu erstellen und speichern Sie den Wert des gefundenen Terminatorcodons in diesem min (nach Überprüfung ist es wirklich min). NICHT return in den if Aussagen verwenden, die nach Terminatorcodons suchen. und Rückgabe der min + 3 erst nach den drei if Anweisungen durchgeführt und bestimmt den tatsächlichen Mindestabstand von "TAG".

Ich hoffe, es war nützlich.

Verwandte Themen