2009-06-28 76 views
5

Tôi đang tạo một trình phân tích cú pháp Brainfuck (trong một phương ngữ BASIC) cuối cùng để tạo ra một thông dịch viên nhưng tôi đã nhận ra nó không thẳng như tôi nghĩ. Vấn đề của tôi là tôi cần một cách để phân tích chính xác các toán tử vòng lặp phù hợp trong một chương trình Brainfuck. Đây là một chương trình ví dụ:Tạo trình phân tích cú pháp Brainfuck, phương pháp phân tích cú pháp vòng lặp tốt nhất là gì?

,>,>++++++++[<------<------>>-] 
<<[>[>+>+<<-]>>[<<+>>-]<<<-] 
>>>++++++[<++++++++>-],<.>. 

'[' = bắt đầu vòng lặp

']' = cuối vòng lặp

tôi cần phải ghi lại điểm bắt đầu và điểm cuối của mỗi nhà khai thác phù hợp với vòng lặp để tôi có thể nhảy xung quanh nguồn khi cần thiết. Một số vòng là một mình, một số được lồng nhau.

Cách tốt nhất để phân tích cú pháp này là gì? Tôi đã suy nghĩ có thể di chuyển qua các tập tin nguồn tạo ra một mảng 2D (hoặc như thế) ghi lại vị trí bắt đầu và kết thúc của mỗi nhà điều hành phù hợp, nhưng điều này có vẻ như rất nhiều 'to'ing và fro'ing' thông qua nguồn. Đây có phải là cách tốt nhất để làm điều đó không?

Thông tin khác: Brainfuck homepage

EDIT: Mã mẫu bằng ngôn ngữ bất kỳ được đánh giá cao.

+0

@Gary, vui lòng xem câu trả lời cập nhật cho hai ví dụ triển khai bằng cách sử dụng ngăn xếp để theo dõi 'điểm nhảy'. Việc đầu tiên là đệ quy trong khi thứ hai là lặp đi lặp lại nhưng cả hai đều làm điều tương tự. Vui lòng cho tôi biết nếu có điều gì đó không rõ ràng để tôi có thể cố làm rõ! –

+0

Cảm ơn. –

Trả lời

11

Bạn đã cân nhắc sử dụng cấu trúc dữ liệu Stack để ghi lại "các điểm nhảy" (tức là vị trí của con trỏ chỉ dẫn).

Vì vậy, về cơ bản, mỗi khi bạn gặp "[", bạn đẩy vị trí hiện tại của con trỏ hướng dẫn trên ngăn xếp này. Bất cứ khi nào bạn gặp phải một "]" bạn đặt lại con trỏ chỉ dẫn đến giá trị hiện đang ở trên cùng của ngăn xếp. Khi một vòng lặp hoàn tất, bạn bật nó ra khỏi ngăn xếp.

Đây là một ví dụ trong C++ với 100 ô bộ nhớ. Mã này xử lý vòng lồng nhau một cách đệ quy và mặc dù nó không được tinh chế nó nên minh họa cho khái niệm ..

char cells[100] = {0}; // define 100 memory cells 
char* cell = cells;  // set memory pointer to first cell 
char* ip = 0;   // define variable used as "instruction pointer" 

void interpret(static char* program, int* stack, int sp) 
{ 
    int tmp; 
    if(ip == 0)    // if the instruction pointer hasn't been initialized 
     ip = program;  // now would be a good time 

    while(*ip)    // this runs for as long as there is valid brainF**k 'code' 
    { 
     if(*ip == ',') 
      *cell = getch(); 
     else if(*ip == '.') 
      putch(*cell); 
     else if(*ip == '>') 
      cell++; 
     else if(*ip == '<') 
      cell--; 
     else if(*ip == '+') 
      *cell = *cell + 1; 
     else if(*ip == '-') 
      *cell = *cell - 1; 
     else if(*ip == '[') 
     {   
      stack[sp+1] = ip - program; 
      *ip++; 
      while(*cell != 0) 
      { 
       interpret(program, stack, sp + 1); 
      } 
      tmp = sp + 1; 
      while((tmp >= (sp + 1)) || *ip != ']') 
      { 
       *ip++; 
       if(*ip == '[') 
        stack[++tmp] = ip - program; 
       else if(*ip == ']') 
        tmp--; 
      }   
     } 
     else if(*ip == ']') 
     { 
      ip = program + stack[sp] + 1; 
      break; 
     } 
     *ip++;  // advance instruction 
    } 
} 

int _tmain(int argc, _TCHAR* argv[]) 
{ 
    int stack[100] = {0}; // use a stack of 100 levels, modeled using a simple array 
    interpret(",>,>++++++++[<------<------>>-]<<[>[>+>+<<-]>>[<<+>>-]<<<-]>>>++++++[<++++++++>-],<.>.", stack, 0); 
    return 0; 
} 

EDIT Tôi chỉ đi qua mã một lần nữa và tôi nhận ra rằng có một lỗi trong vòng lặp while mà có 'bỏ qua' vòng phân tích cú pháp nếu giá trị của con trỏ là 0. Đây là nơi tôi thực hiện thay đổi:

while((tmp >= (sp + 1)) || *ip != ']')  // the bug was tmp > (sp + 1) 
{ 
ip++; 
if(*ip == '[') 
    stack[++tmp] = ip - program; 
else if(*ip == ']') 
    tmp--; 
} 

Dưới đây là một thực hiện các phân tích cú pháp tương tự, nhưng mà không sử dụng đệ quy:

char cells[100] = {0}; 
void interpret(static char* program) 
{ 
    int cnt;    // cnt is a counter that is going to be used 
          //  only when parsing 0-loops 
    int stack[100] = {0}; // create a stack, 100 levels deep - modeled 
          //  using a simple array - and initialized to 0 
    int sp = 0;   // sp is going to be used as a 'stack pointer' 
    char* ip = program; // ip is going to be used as instruction pointer 
          // and it is initialized at the beginning or program 
    char* cell = cells; // cell is the pointer to the 'current' memory cell 
          //  and as such, it is initialized to the first 
          //  memory cell 

    while(*ip)    // as long as ip point to 'valid code' keep going 
    { 
     if(*ip == ',') 
      *cell = getch(); 
     else if(*ip == '.') 
      putch(*cell); 
     else if(*ip == '>') 
      cell++; 
     else if(*ip == '<') 
      cell--; 
     else if(*ip == '+') 
      *cell = *cell + 1; 
     else if(*ip == '-') 
      *cell = *cell - 1; 
     else if(*ip == '[') 
     {   
      if(stack[sp] != ip - program) 
       stack[++sp] = ip - program; 

      *ip++; 

      if(*cell != 0) 
       continue; 
      else 
      {     
       cnt = 1; 
       while((cnt > 0) || *ip != ']') 
       { 
        *ip++; 
        if(*ip == '[') 
        cnt++; 
        else if(*ip == ']') 
        cnt--; 
       } 
       sp--; 
      } 
     }else if(*ip == ']') 
     {    
      ip = program + stack[sp]; 
      continue; 
     } 
     *ip++; 
    } 
} 

int _tmain(int argc, _TCHAR* argv[]) 
{ 
    // define our program code here.. 
    char *prg = ",>++++++[<-------->-],[<+>-]<."; 

    interpret(prg); 
    return 0; 
} 
+1

bạn không biết ý tưởng thiên tài của bạn là +1 !!!!!!!!!!!!!!!!!!! Cảm ơn! –

1

Mỗi khi bạn tìm thấy dấu '[', hãy đẩy vị trí hiện tại (hoặc mã thông báo "điểm đánh dấu" khác hoặc "ngữ cảnh") trên ngăn xếp. Khi bạn đi qua một ']', bạn đang ở cuối vòng lặp, và bạn có thể bật mã thông báo điểm đánh dấu từ ngăn xếp.

Vì trong BF '[' đã kiểm tra điều kiện và có thể cần phải nhảy qua ']', bạn có thể muốn có một lá cờ chỉ ra rằng các lệnh sẽ bị bỏ qua trong ngữ cảnh vòng lặp hiện tại.

0

Tôi không có mã mẫu, nhưng.

tôi có thể thử sử dụng một chồng, cùng với một thuật toán như thế này:

  1. (thực hiện dòng lệnh)
  2. Encounter một [
  3. Nếu con trỏ == 0, sau đó tiếp tục đọc cho đến khi bạn gặp ']', và không thực hiện bất kỳ chỉ dẫn nào cho đến khi bạn đến được nó. Bước 1 1.
  4. Nếu con trỏ! = 0, sau đó đẩy vị trí đó lên một chồng.
  5. Tiếp tục thực hiện những lệnh
  6. Nếu bạn gặp một]
  7. Nếu con trỏ == 0, bật [off của ngăn xếp, và tiến hành (goto bước 1)
  8. Nếu con trỏ! = 0, lén nhìn trên cùng của ngăn xếp và chuyển đến vị trí đó. (Goto bước 5)
+0

Bước 3 yêu cầu inorder counter để xử lý chính xác các vòng lặp lồng nhau. Đó là lý do tại sao tôi sẽ sử dụng cùng một mã như khi xử lý các hướng dẫn, nhưng bỏ qua chúng. – Lucero

1

Python 3.0 ví dụ về thuật toán ngăn xếp được mô tả bởi các áp phích khác:.

(Vâng, phải trung thực, điều này chỉ thấy dấu ngoặc hợp tôi không biết brainf * ck, vì vậy phải làm gì tiếp theo, tôi không biết.)

2

Đủ thú vị, chỉ vài ngày trước, tôi đã viết một trình thông dịch bộ não trong Java.

Một trong những vấn đề tôi gặp phải là giải thích các lệnh tại official page là không đủ và không đề cập đến phần về vòng lặp lồng nhau. Wikipedia page on Brainf*ck có tiểu mục Commands mô tả hành vi đúng.

Về cơ bản để tóm tắt sự cố, trang chính thức cho biết khi lệnh là [ và vị trí bộ nhớ hiện tại là 0, sau đó chuyển đến ] tiếp theo. Hành vi đúng là chuyển đến tương ứng], không phải là hành động tiếp theo.

Một cách để đạt được hành vi này là theo dõi mức độ lồng ghép. Tôi đã kết thúc việc thực hiện điều này bằng cách có một truy cập mà theo dõi mức độ làm tổ.

Sau đây là một phần của vòng lặp chính của thông dịch viên:

do { 
    if (inst[pc] == '>') { ... } 
    else if (inst[pc] == '<') { ... } 
    else if (inst[pc] == '+') { ... } 
    else if (inst[pc] == '-') { ... } 
    else if (inst[pc] == '.') { ... } 
    else if (inst[pc] == ',') { ... } 
    else if (inst[pc] == '[') { 
    if (memory[p] == 0) { 
     int nesting = 0; 

     while (true) { 
     ++pc; 

     if (inst[pc] == '[') { 
      ++nesting; 
      continue; 
     } else if (nesting > 0 && inst[pc] == ']') { 
      --nesting; 
      continue; 
     } else if (inst[pc] == ']' && nesting == 0) { 
      break; 
     } 
     } 
    } 
    } 
    else if (inst[pc] == ']') { 
    if (memory[p] != 0) { 
     int nesting = 0; 

     while (true) { 
     --pc; 

     if (inst[pc] == ']') { 
      ++nesting; 
      continue; 
     } else if (nesting > 0 && inst[pc] == '[') { 
      --nesting; 
      continue; 
     } else if (inst[pc] == '[' && nesting == 0) { 
      break; 
     } 
     } 
    } 
    } 
} while (++pc < inst.length); 

Đây là huyền thoại cho tên biến:

  • memory - các tế bào bộ nhớ cho dữ liệu.
  • p - trỏ đến vị trí ô nhớ hiện tại.
  • inst - một mảng giữ các hướng dẫn.
  • pc - bộ đếm chương trình; trỏ đến lệnh hiện tại.
  • nesting - mức độ lồng của vòng lặp hiện tại. nesting của 0 có nghĩa là vị trí hiện tại không nằm trong vòng lặp lồng nhau.

Về cơ bản, khi mở vòng lặp [, vị trí bộ nhớ hiện tại được kiểm tra xem giá trị có là 0 hay không. Nếu đúng như vậy, một vòng lặp while được nhập để chuyển đến ] tương ứng.

Cách làm tổ được xử lý như sau:

  1. Nếu một [ đang gặp phải trong khi tìm kiếm các vòng lặp tương ứng đóng ], sau đó biến nesting được tăng lên bởi 1 để chỉ ra rằng chúng ta có đã nhập một vòng lặp lồng nhau.

  2. Nếu một ] đang gặp phải, và:

    a. Nếu biến số nesting lớn hơn 0 thì biến số nesting bị giảm đi 1 để cho biết rằng chúng tôi đã để lại vòng lặp lồng nhau.

    b. Nếu biến số nesting0, thì chúng tôi biết rằng đã kết thúc vòng lặp, do đó, tìm kiếm kết thúc vòng lặp trong vòng lặp while bị chấm dứt bằng cách thực hiện câu lệnh break.

Bây giờ, phần tiếp theo là xử lý việc đóng vòng lặp theo ]. Tương tự như việc mở vòng lặp, nó sẽ sử dụng bộ đếm nesting để xác định mức lồng hiện tại của vòng lặp và cố gắng tìm vòng mở tương ứng [.

Phương pháp này có thể không phải là cách thanh lịch nhất để làm mọi thứ, nhưng có vẻ như nó thân thiện với tài nguyên vì nó chỉ yêu cầu thêm một biến để sử dụng làm bộ đếm cho mức lồng hiện tại.

(Tất nhiên, "nguồn thân thiện" được bỏ qua thực tế là thông dịch viên này được viết bằng Java - Tôi chỉ muốn viết một số mã nhanh chóng và Java vừa xảy ra là những gì tôi đã viết nó trong.)

+0

+1 để đề xuất số nguyên thay vì một ngăn xếp. Tại sao mọi người lại muốn một ngăn xếp ??! –

1

Và đây là cùng một mã tôi đã đưa ra như là một ví dụ trước đó trong C + +, nhưng chuyển sang VB.NET. Tôi quyết định đăng nó ở đây vì Gary đã đề cập đến việc anh ta đang cố gắng viết trình phân tích cú pháp của mình bằng một phương ngữ BASIC.

Public cells(100) As Byte 

Sub interpret(ByVal prog As String) 
    Dim program() As Char 

    program = prog.ToCharArray() ' convert the input program into a Char array 

    Dim cnt As Integer = 0  ' a counter to be used when skipping over 0-loops          
    Dim stack(100) As Integer  ' a simple array to be used as stack 
    Dim sp As Integer = 0   ' stack pointer (current stack level) 
    Dim ip As Integer = 0   ' Instruction pointer (index of current instruction) 
    Dim cell As Integer = 0  ' index of current memory 

    While (ip < program.Length) ' loop over the program 
     If (program(ip) = ",") Then 
      cells(cell) = CByte(AscW(Console.ReadKey().KeyChar)) 
     ElseIf (program(ip) = ".") Then 
      Console.Write("{0}", Chr(cells(cell))) 
     ElseIf (program(ip) = ">") Then 
      cell = cell + 1 
     ElseIf (program(ip) = "<") Then 
      cell = cell - 1 
     ElseIf (program(ip) = "+") Then 
      cells(cell) = cells(cell) + 1 
     ElseIf (program(ip) = "-") Then 
      cells(cell) = cells(cell) - 1 
     ElseIf (program(ip) = "[") Then 
      If (stack(sp) <> ip) Then 
       sp = sp + 1 
       stack(sp) = ip 
      End If 

      ip = ip + 1 

      If (cells(cell) <> 0) Then 
       Continue While 
      Else 
       cnt = 1 
       While ((cnt > 0) Or (program(ip) <> "]")) 
        ip = ip + 1 
        If (program(ip) = "[") Then 
         cnt = cnt + 1 
        ElseIf (program(ip) = "]") Then 
         cnt = cnt - 1 
        End If 
       End While 
       sp = sp - 1 
      End If 
     ElseIf (program(ip) = "]") Then 
      ip = stack(sp) 
      Continue While 
     End If 
     ip = ip + 1 
    End While 
End Sub 

Sub Main() 
    ' invoke the interpreter 
    interpret(",>++++++[<-------->-],[<+>-]<.") 
End Sub 
0

Câu hỏi này hơi cũ nhưng tôi muốn nói rằng câu trả lời ở đây đã giúp tôi quyết định lộ trình khi viết trình thông dịch Brainf ** k của riêng tôi. Đây là sản phẩm cuối cùng:

#include <stdio.h> 

char *S[9999], P[9999], T[9999], 
    **s=S, *p=P, *t=T, c, x; 

int main() { 
    fread(p, 1, 9999, stdin); 
    for (; c=*p; ++p) { 
     if (c == ']') { 
      if (!x) 
       if (*t) p = *(s-1); 
       else --s; 
      else --x; 
     } else if (!x) { 
      if (c == '[') 
       if (*t) *(s++) = p; 
       else ++x; 
      } 

      if (c == '<') t--; 
      if (c == '>') t++; 
      if (c == '+') ++*t; 
      if (c == '-') --*t; 
      if (c == ',') *t = getchar(); 
      if (c == '.') putchar(*t); 
     } 
    } 
} 
+0

đẹp và đơn giản! –

+0

Việc lồng vòng không hoạt động. – user3710044

3

Phương pháp kinh điển để phân tích cú pháp ngữ cảnh là sử dụng ngăn xếp. Bất cứ điều gì khác và bạn đang làm việc quá chăm chỉ và mạo hiểm đúng đắn.

Bạn có thể muốn sử dụng trình tạo trình phân tích cú pháp như tách hoặc yacc, vì rất nhiều công việc bẩn được thực hiện cho bạn, nhưng với ngôn ngữ đơn giản như BF, nó có thể quá mức cần thiết.

-1

Dường như câu hỏi này đã trở thành cuộc thăm dò "đăng bf thông dịch viên của bạn".

Vì vậy, đây là của tôi mà tôi chỉ có làm việc:

#include <assert.h> 
#include <stdlib.h> 
#include <stdio.h> 
#include <string.h> 
#include <sys/mman.h> 
#include <sys/types.h> 
#include <sys/stat.h> 
#include <fcntl.h> 
#include <unistd.h> 

void error(char *msg) { 
    fprintf(stderr, "Error: %s\n", msg); 
} 

enum { MEMSIZE = 30000 }; 

char *mem; 
char *ptr; 
char *prog; 
size_t progsize; 

int init(char *progname) { 
    int f,r; 
    struct stat fs; 
    ptr = mem = calloc(MEMSIZE, 1); 
    f = open(progname, O_RDONLY); 
    assert(f != -1); 
    r = fstat(f, &fs); 
    assert(r == 0); 
    prog = mmap(NULL, progsize = fs.st_size, PROT_READ, MAP_PRIVATE, f, 0); 
    assert(prog != NULL); 
    return 0; 
} 

int findmatch(int ip, char src){ 
    char *p="[]"; 
    int dir[]= { 1, -1 }; 
    int i; 
    int defer; 
    i = strchr(p,src)-p; 
    ip+=dir[i]; 
    for (defer=dir[i]; defer!=0; ip+=dir[i]) { 
     if (ip<0||ip>=progsize) error("mismatch"); 
     char *q = strchr(p,prog[ip]); 
     if (q) { 
      int j = q-p; 
      defer+=dir[j]; 
     } 
    } 
    return ip; 
} 

int run() { 
    int ip; 
    for(ip = 0; ip>=0 && ip<progsize; ip++) 
     switch(prog[ip]){ 
     case '>': ++ptr; break; 
     case '<': --ptr; break; 
     case '+': ++*ptr; break; 
     case '-': --*ptr; break; 
     case '.': putchar(*ptr); break; 
     case ',': *ptr=getchar(); break; 
     case '[': /*while(*ptr){*/ 
        if (!*ptr) ip=findmatch(ip,'['); 
        break; 
     case ']': /*}*/ 
        if (*ptr) ip=findmatch(ip,']'); 
        break; 
     } 

    return 0; 
} 

int cleanup() { 
    free(mem); 
    ptr = NULL; 
    return 0; 
} 

int main(int argc, char *argv[]) { 
    init(argc > 1? argv[1]: NULL); 
    run(); 
    cleanup(); 
    return 0; 
} 
+0

Câu hỏi này đang tìm kiếm * giải thích *, không chỉ đơn giản là cho mã làm việc. Câu trả lời của bạn không cung cấp thông tin chi tiết cho người hỏi và có thể bị xóa. Vui lòng [sửa] để giải thích cách giải quyết vấn đề này. –

0
package interpreter; 

import java.awt.event.ActionListener; 

import javax.swing.JTextPane; 

public class Brainfuck { 

    final int tapeSize = 0xFFFF; 
    int tapePointer = 0; 
    int[] tape = new int[tapeSize]; 
    int inputCounter = 0; 

    ActionListener onUpdateTape; 

    public Brainfuck(byte[] input, String code, boolean debugger, 
      JTextPane output, ActionListener onUpdate) { 
     onUpdateTape = onUpdate; 
     if (debugger) { 
      debuggerBF(input, code, output); 
     } else { 
      cleanBF(input, code, output); 
     } 
    } 

    private void debuggerBF(byte[] input, String code, JTextPane output) { 
     for (int i = 0; i < code.length(); i++) { 
      onUpdateTape.actionPerformed(null); 
      switch (code.charAt(i)) { 
      case '+': { 
       tape[tapePointer]++; 
       break; 
      } 
      case '-': { 
       tape[tapePointer]--; 
       break; 
      } 
      case '<': { 
       tapePointer--; 
       break; 
      } 
      case '>': { 
       tapePointer++; 
       break; 
      } 
      case '[': { 
       if (tape[tapePointer] == 0) { 
        int nesting = 0; 

        while (true) { 
         ++i; 

         if (code.charAt(i) == '[') { 
          ++nesting; 
          continue; 
         } else if (nesting > 0 && code.charAt(i) == ']') { 
          --nesting; 
          continue; 
         } else if (code.charAt(i) == ']' && nesting == 0) { 
          break; 
         } 
        } 
       } 
       break; 
      } 
      case ']': { 
       if (tape[tapePointer] != 0) { 
        int nesting = 0; 

        while (true) { 
         --i; 

         if (code.charAt(i) == ']') { 
          ++nesting; 
          continue; 
         } else if (nesting > 0 && code.charAt(i) == '[') { 
          --nesting; 
          continue; 
         } else if (code.charAt(i) == '[' && nesting == 0) { 
          break; 
         } 
        } 
       } 
       break; 
      } 
      case '.': { 
       output.setText(output.getText() + (char) (tape[tapePointer])); 
       break; 
      } 
      case ',': { 
       tape[tapePointer] = input[inputCounter]; 
       inputCounter++; 
       break; 
      } 
      } 
     } 
    } 

    private void cleanBF(byte[] input, String code, JTextPane output) { 
     for (int i = 0; i < code.length(); i++) { 
      onUpdateTape.actionPerformed(null); 
      switch (code.charAt(i)) { 
      case '+':{ 
       tape[tapePointer]++; 
       break; 
      } 
      case '-':{ 
       tape[tapePointer]--; 
       break; 
      } 
      case '<':{ 
       tapePointer--; 
       break; 
      } 
      case '>':{ 
       tapePointer++; 
       break; 
      } 
      case '[': { 
       if (tape[tapePointer] == 0) { 
        int nesting = 0; 

        while (true) { 
         ++i; 

         if (code.charAt(i) == '[') { 
          ++nesting; 
          continue; 
         } else if (nesting > 0 && code.charAt(i) == ']') { 
          --nesting; 
          continue; 
         } else if (code.charAt(i) == ']' && nesting == 0) { 
          break; 
         } 
        } 
       } 
       break; 
      } 
      case ']': { 
       if (tape[tapePointer] != 0) { 
        int nesting = 0; 

        while (true) { 
         --i; 

         if (code.charAt(i) == ']') { 
          ++nesting; 
          continue; 
         } else if (nesting > 0 && code.charAt(i) == '[') { 
          --nesting; 
          continue; 
         } else if (code.charAt(i) == '[' && nesting == 0) { 
          break; 
         } 
        } 
       } 
       break; 
      } 
      case '.':{ 
       output.setText(output.getText()+(char)(tape[tapePointer])); 
       break; 
      } 
      case ',':{ 
       tape[tapePointer] = input[inputCounter]; 
       inputCounter++; 
       break; 
      } 
      } 
     } 
    } 

    public int[] getTape() { 
     return tape; 
    } 

    public void setTape(int[] tape) { 
     this.tape = tape; 
    } 

    public void editTapeValue(int counter, int value) { 
     this.tape[counter] = value; 
    } 

} 

này nên làm việc. Bạn cần phải sửa đổi nó một chút. Đó thực sự là ví dụ tiêu chuẩn về cách thức hoạt động của trình thông dịch brainfuck. Tôi đã sửa đổi nó để sử dụng trong ứng dụng của tôi, khung được xử lý ở đó:

case '[': { 
    if (tape[tapePointer] == 0) { 
     int nesting = 0; 

     while (true) { 
      ++i; 

      if (code.charAt(i) == '[') { 
       ++nesting; 
       continue; 
      } 
      else if (nesting > 0 && code.charAt(i) == ']') { 
       --nesting; 
       continue; 
      } 
      else if (code.charAt(i) == ']' && nesting == 0) { 
       break; 
      } 
     } 
    } 
    break; 
} 
case ']': { 
    if (tape[tapePointer] != 0) { 
     int nesting = 0; 

     while (true) { 
      --i; 

      if (code.charAt(i) == ']') { 
       ++nesting; 
       continue; 
      } 
      else if (nesting > 0 && code.charAt(i) == '[') { 
       --nesting; 
       continue; 
      } 
      else if (code.charAt(i) == '[' && nesting == 0) { 
       break; 
      } 
     } 
    } 
    break; 
} 
+0

Chào mừng bạn đến với Stack Overflow! Mặc dù mã này có thể giúp giải quyết vấn đề, nó không giải thích _why_ và/hoặc _how_ nó trả lời câu hỏi. Việc cung cấp ngữ cảnh bổ sung này sẽ cải thiện đáng kể giá trị giáo dục lâu dài của nó. Vui lòng [sửa] câu trả lời của bạn để thêm giải thích, bao gồm những giới hạn và giả định được áp dụng. –

Các vấn đề liên quan