Java: 1523 1512 ký tự
import java.util.*;class W{int v=99;Map<Integer,String>t;boolean k;public static void main(String[]y){new W().d();}W(){try{java.io.InputStream i=new java.io.File("r").toURL().openStream();t=new HashMap<>();int a=0,x=0,y=0;while((a=i.read())>-1){if(a==10){y++;x=0;continue;}q(x,y,(a>47&a<58?"!":"")+(char)a);x++;}}catch(Exception e){}}void d(){while(!k){k=!k;for(Map.Entry<Integer,String>g:t.entrySet())e(g.getKey(),g.getValue());}for(String b:t.values())if(b.startsWith("$"))System.out.println(b.substring(1));}void e(int a,String s){if(s==null||!s.startsWith("!"))return;int x=a/v,y=a%v;s=s.substring(1);b(s,x,y,x-1,y+1);b(s,x,y,x,y+1);b(s,x,y,x+1,y+1);b(s,x,y,x-1,y);b(s,x,y,x+1,y);b(s,x,y,x-1,y-1);b(s,x,y,x,y-1);b(s,x,y,x+1,y-1);}void b(String p,int m,int n,int x,int y){String s=t.get(x*v+y);if(s==null)return;boolean g=y==n+1;boolean h=y==n-1;boolean i=x==m+1;boolean j=x==m-1;if(z(s,"-=")&n==y){if(i)b(p,x,y,x+1,y);if(j)b(p,x,y,x-1,y);}if(z(s,"|=")&m==x){if(g)b(p,x,y,x,y+1);if(h)b(p,x,y,x,y-1);}if(z(s,"/=")){if(j&g)b(p,x,y,x-1,y+1);if(i&h)b(p,x,y,x+1,y-1);}if(z(s,"\\=")){if(i&g)b(p,x,y,x+1,y+1);if(j&h)b(p,x,y,x-1,y-1);}if(z(s,".")){q(x,y,"!"+p);u();}if(z(s,"~")){q(x,y,"!~("+p+")");u();}if((s.charAt(0)=='%'&n==y-1)|(s.charAt(0)=='&'&n==y+1)){q(x,y,"!("+p+")"+s.charAt(1)+"("+s.substring(2)+")");u();}if(z(s,"OoAaXx")){q(x,y,(n==y+1?"%":"&")+s+p);u();}if(z(s,":")){q(x,y,"$"+p);u();}}void q(int x,int y,String z){t.put(x*v+y,z);}void u(){k=false;}boolean z(String s,String c){return c.indexOf(s)>-1;}}
Nó cung cấp đầu ra này cho đầu vào mẫu:
(~(((5)X(4))O(3)))a(~(1))
((~(((5)X(4))O(3)))a(~(1)))X(((2)x(1))x(3))
Để ép kích thước của nó:
- Nó không thực hiện bất kỳ kiểm tra lỗi, xử lý lỗi hoặc xác nhận đầu vào, giả sử rằng đầu vào luôn hợp lệ.
- Được giới hạn ở 99 dòng đầu vào.
- Tệp đầu vào của nó phải được gọi chỉ
r
, không có bất kỳ phần mở rộng tệp nào trong tên.
- Nó không thực hiện bất kỳ nỗ lực nào để phát hiện nếu dấu ngoặc đơn là hoặc không cần thiết. Nó giả định rằng chúng luôn luôn cần thiết và vì giả định này là sai, nên có nhiều dấu ngoặc đơn hơn mức cần thiết, nhưng vì điều này không làm cho nó thất bại trong thông số kỹ thuật, nên không có vấn đề gì.
- Thứ tự của các tham số cho mỗi toán tử nhị phân nói chung là không thể đoán trước, vì nó phụ thuộc vào vận tốc mà các giá trị được truyền và từ thứ tự quét tế bào. Nhưng vì tất cả các toán tử nhị phân là giao hoán, nên điều này không có vấn đề gì.
Tôi chắc chắn rằng nó sẽ có thể giảm nó nhiều hơn, nhưng chỉ một chút.
Trình thông dịch được thực hiện dưới dạng một số loại automata di động. Nó quét toàn bộ giá trị cài đặt trường, lặp lại nhiều lần nếu cần cho đến khi không có thay đổi nào được phát hiện.
Đây là một phiên bản chưa được chỉnh sửa:
import java.util.*;
class Wiring {
int maxLines = 99;
Map<Integer, String> circuitState;
boolean finished;
public static void main(String[] args) {
new Wiring().interpret();
}
Wiring() {
try {
// Always read the input from the "r" file, and do not check if it even
// exists. BTW, the toURL() method is deprecated, but we don't care about
// this in code-golfing.
java.io.InputStream stream = new java.io.File("r").toURL().openStream();
circuitState = new HashMap<>();
int byteRead = 0, cellX = 0, cellY = 0;
while ((byteRead = stream.read()) > -1) {
// Check for line break;
if (byteRead == 10) {
cellY++;
cellX = 0;
continue;
}
// Populate the circuit cell. Precede numbers with an exclamation mark.
setCircuitCell(cellX, cellY, (byteRead >= '0' & byteRead <= '9' ? "!" : "") + (char) byteRead);
cellX++;
} catch (Exception e) {
}
}
void interpret() {
while (!finished) {
finished = !finished; // i.e. finished = false;
for (Map.Entry<Integer, String> entry : circuitState.entrySet()) {
analyzeCell(entry.getKey(), entry.getValue());
}
}
// Now print the output. To do that scan for cells marked with "$".
for (String cell : circuitState.values()) {
if (cell.startsWith("$")) System.out.println(cell.substring(1));
}
}
void analyzeCell(int cellIndex, String cellValue) {
// Only the cells with a value marked with "!" are worth to analyze.
if (cellValue == null || !cellValue.startsWith("!")) return;
// Convert the cellIndex to a bidimensional coordinate.
int x = cellIndex / maxLines, y = cellIndex % maxLines;
// Remove the "!".
cellValue = cellValue.substring(1);
// Propagate the cell value to neighbouring cells.
propagateCellData(cellValue, x, y, x - 1, y + 1);
propagateCellData(cellValue, x, y, x, y + 1);
propagateCellData(cellValue, x, y, x + 1, y + 1);
propagateCellData(cellValue, x, y, x - 1, y);
propagateCellData(cellValue, x, y, x + 1, y);
propagateCellData(cellValue, x, y, x - 1, y - 1);
propagateCellData(cellValue, x, y, x, y - 1);
propagateCellData(cellValue, x, y, x + 1, y - 1);
}
void propagateCellData(String cellValue, int sourceX, int sourceY, int targetX, int targetY) {
String targetContent = circuitState.get(targetX * maxLines + targetY);
// If the target cell does not exist, just ignore.
if (targetContent == null) return;
boolean targetBelowSource = targetY == sourceY + 1;
boolean targetAboveSource = targetY == sourceY - 1;
boolean targetRightToSource = targetX == sourceX + 1;
boolean targetLeftToSource = targetX == sourceX - 1;
// Propagate horizontally through wires.
if (isStringContained(targetContent, "-=") & sourceY == targetY) {
if (targetRightToSource) propagateCellData(cellValue, targetX, targetY, targetX + 1, targetY);
if (targetLeftToSource) propagateCellData(cellValue, targetX, targetY, targetX - 1, targetY);
}
// Propagate vertically.
if (isStringContained(targetContent, "|=") & sourceX == targetX) {
if (targetBelowSource) propagateCellData(cellValue, targetX, targetY, targetX, targetY + 1);
if (targetAboveSource) propagateCellData(cellValue, targetX, targetY, targetX, targetY - 1);
}
// Propagate in the diagonal x=-y.
if (isStringContained(targetContent, "/=")) {
if (targetLeftToSource & targetBelowSource) {
propagateCellData(cellValue, targetX, targetY, targetX - 1, targetY + 1);
}
if (targetRightToSource & targetAboveSource) {
propagateCellData(cellValue, targetX, targetY, targetX + 1, targetY - 1);
}
}
// Propagate in the diagonal x=y.
if (isStringContained(targetContent, "\\=")) {
if (targetRightToSource & targetBelowSource) {
propagateCellData(cellValue, targetX, targetY, targetX + 1, targetY + 1);
}
if (targetLeftToSource & targetAboveSource) {
propagateCellData(cellValue, targetX, targetY, targetX - 1, targetY - 1);
}
}
// If we got a dot, store the value there.
// Do not forget to mark it with "!", so we can rescan it later.
if (isStringContained(targetContent, ".")) {
setCircuitCell(targetX, targetY, "!" + cellValue);
markThatStateChanged();
}
// If we got a "~", store the inverted value there.
// Do not forget to mark it with "!", so we can rescan it later.
if (isStringContained(targetContent, "~")) {
setCircuitCell(targetX, targetY, "!~(" + cellValue + ")");
markThatStateChanged();
}
// If we found a binary logical port with one of the values set and
// we can set the another value, do it. Use "%" and "&" to know which
// one was already defined.
// BTW, do not forget to mark it with "!", so we can rescan it later.
if ((targetContent.charAt(0) == '%' & sourceY == targetY - 1)
| (targetContent.charAt(0) == '&' & sourceY == targetY + 1))
{
setCircuitCell(targetX, targetY,
"!(" + cellValue + ")"
+ targetContent.charAt(1)
+ "(" + targetContent.substring(2) + ")");
markThatStateChanged();
}
// Found a binary logical port without any value setted, so set it.
// Use "%" and "&" to mark which one was setted.
if (isStringContained(targetContent, "OoAaXx")) {
setCircuitCell(targetX, targetY, (sourceY == targetY + 1 ? "%" : "&") + targetContent + cellValue);
markThatStateChanged();
}
// If we found an output, store the value there.
// Mark it with "$", so we will print it in the future.
if (isStringContained(targetContent, ":")) {
setCircuitCell(targetX, targetY, "$" + cellValue);
markThatStateChanged();
}
}
void setCircuitCell(int cellX, int cellY, String cellContents) {
circuitState.put(cellX * maxLines + cellY, cellContents);
}
void markThatStateChanged() {
finished = false;
}
boolean isStringContained(String searchingString, String searchTarget) {
return searchTarget.indexOf(searchingString) > -1;
}
}