现在的位置: 首页 > 综合 > 正文

Brainfuck VM

2014年01月04日 ⁄ 综合 ⁄ 共 1832字 ⁄ 字号 评论关闭
package org.vizee.brainfuckvm;

public class BrainfuckVM {
	
	private byte[] ds;
	private byte[] cs;
	private int[] es;
	private int dp;
	
	private void ds_resize(int size, boolean preserve)
	{
		byte[] backup = null;
		if(preserve && ds != null)
			backup = ds;
		ds = new byte[size];
		if(backup != null)
			System.arraycopy(ds, 0, backup, 0, Math.min(backup.length, size));
		return;
	}
	
	public int run()
	{
		if(cs == null)
			return 1;
		ds_resize(1024, false);
		dp = 0;
		for(int i = 0;i < cs.length;i++) {
			switch(cs[i]) {
			case 0x1: //+ | -
				ds[dp] += es[i];
				break;
			case 0x2: //< | >
				dp += es[i];
				if(dp >= ds.length)
					ds_resize(dp + 1024, true);
				else if(dp < 0) {
					ds = null;
					return 0;
				}
				break;
			case 0x4: //,
				try {
					ds[dp] = (byte)System.in.read();
				} catch (Exception e) {
					System.out.println(e.toString());
				}
				break;
			case 0x6: //.
				System.out.print((char)ds[dp]);
				break;
			case 0x8: //[
				if(ds[dp] == 0)
					i = es[i];
				break;
			case 0xa: //]
				if(ds[dp] != 0)
					i = es[i];
				break;
			}
		}
		ds = null;
		return 0;
	}
	
	public int load(String code)
	{
		int length = 0;
		char[] stream = code.toCharArray();
		int count = 0;
		for(int i = 0;i < stream.length;i++) {
			switch(stream[i]) {
			case '[':
				count++;
			case ']':
				if(stream[i] == ']') {
					if(count == 0)
						return 0;
					count--;
				}
			case ',':
			case '.':
				length++;
				break;
			case '+':
			case '-':
			case '<':
			case '>':
				int j;
				for(j = i + 1;j < stream.length;j++)
					if(stream[i] != stream[j])
						break;
				i = j - 1;
				length++;
			}
		}
		if(count == 0 && length > 0) {
			cs = new byte[length];
			es = new int[length];
			int[] match = new int[length];
			int current = 0;
			count = 0;
			for(int i = 0;i < stream.length;i++) {
				switch(stream[i]) {
				case '[':
					cs[current] = 0x8;
					match[count++] = current;
					break;
				case ']':
					cs[current] = 0xa;
					es[current] = match[--count];
					es[es[current]] = current;
					break;
				case ',':
					cs[current] = 0x4;
					break;
				case '.':
					cs[current] = 0x6;
					break;
				case '+':
				case '-':
				case '<':
				case '>':
					int j;
					for(j = i + 1;j < stream.length;j++)
						if(stream[i] != stream[j])
							break;
					if(stream[i] == '<' || stream[i] == '>')
						cs[current] = 0x2;
					else
						cs[current] = 0x1;
					if(stream[i] == '<' || stream[i] == '-')
						es[current] = i - j;
					else
						es[current] = j - i;
					i = j - 1;
				}
				if(cs[current] != 0)
					current++;
			}
		}
		return length;
	}
	
	public BrainfuckVM()
	{
		cs = null;
		ds = null;
		es = null;
		dp = 0;
	}
	
}

【上篇】
【下篇】

抱歉!评论已关闭.