每当当前行包含一些特定关键字时,我的程序就必须缩进文本文件中的文本,而不能使用数组或任何正则表达式。
例如
start
write "enter your name
read name
write "enter your age"
read age
if age==100 then
do
print "you stink"
while age !=100
end if
while something
if something
do something
while something
end if
end
应该是:
start
write "enter your name"
read name
write "enter your age"
read age
if age==100 then
do
print "you stink"
while age !=100
end if
while something
if something
do something
while something
end if
end
我无法让我的程序正确缩进第一个“关键字”之后的内容。关键字是“何时,是否,执行,如果,结束,结束,开始等...”
我不允许使用数组或任何正则表达式
我的读取文本文件的代码的一部分:
String corrIndent (String pseudocode2) {
String sTrim = ""; //pseudocode to return
String sTmp;
int debut = 0; //current line start index
int fin; //current line end index
fin = pseudocode2.indexOf("\n", debut);//read lines
do {
//extracts current line
sTmp = pseudocode2.substring(debut, fin);
//opens the do..while loop indent level
if(sTmp.contains("do")){//opens do indent(indents 1 level)
for (int i=1;i<=999;i++){
sTmp =pseudocode2.substring(debut, fin);
//sTrim="\t";
if (sTmp.contains("while")){//close do indent (reduce indentation 1 level)
i=999;//supposes that the text file is never that long
}
//add current line to string to return
//with a newline.
sTrim = sTrim + sTmp+ ""+" ";
//ajuster le debut de la ligne courante suivante
debut = fin + 1;
//trouver la fin de la ligne courante suivante
fin = pseudocode2.indexOf("\n", debut);
}
}
{//when no more indentation is needed
sTrim = sTrim + sTmp + "\n";
debut = fin + 1;
fin = pseudocode2.indexOf("\n", debut);
}
}while (fin != -1);
return sTrim;
}
使用此代码,我可以正确缩进do块,但是如果该do块内有另一个关键字,则不会获得新的缩进级别。
那是为什么?
我尝试了许多方法来将缩进级别保存为变量,但没有成功。
答案 0 :(得分:2)
此解决方案同时使用数组和正则表达式-我将在此处发布,以供将来可能没有此限制的编码人员使用。
这是我刚刚整理的一个快速样本。它使您可以设置要缩进的单词数组,以及哪些单词应触发缩进。
还有一些改进的余地,因为它无法满足您可能需要的所有情况。
您还需要实现将输出写入文件。
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
public class Main {
public static void main(String[] args) {
final String IN_FILE = "test.txt";
final String OUT_FILE = "sample/indent/result.txt";
final int INDENT_SPACES = 4; // Number of spaces to indent
StringBuilder output = new StringBuilder();
int currentIndentLevel = 0;
// Increase indent level on these keywords
String[] keywordsIn = {"start", "if", "do"};
// Decrease indent level on these keywords
String[] keywordsOut = {"while", "end"};
// Read the file, line by line
try {
BufferedReader reader = new BufferedReader(new FileReader(IN_FILE));
String line = reader.readLine();
while (line != null) {
// Indent the line based on current level
for (int i = 0; i < INDENT_SPACES * currentIndentLevel; i++) {
output.append(" ");
}
output.append(line).append("\n");
// Check if it contains a keyword
for (int i = 0; i < keywordsIn.length; i++) {
// Line begins with a keyword to increase the indent
if (line.matches(keywordsIn[i] + "\\b.*")) {
currentIndentLevel += 1; // Increase the indent level
}
}
for (int i = 0; i < keywordsOut.length; i++) {
// Line begins with a keyword to decrease the indent
if (line.matches(keywordsOut[i] + "\\b.*")) {
currentIndentLevel -= 1; // Decrease the indent level
}
}
// Get next line
line = reader.readLine();
}
} catch (IOException e) {
e.printStackTrace();
}
System.out.println(output.toString());
}
}
以原始输入文件为例,该程序将输出以下内容:
start
write "enter your name
read name
write "enter your age"
read age
if age==100 then
do
print "you stink"
while age !=100
end if
while something
if something
do something
while something
end if
end
答案 1 :(得分:0)
所以这是答案的一个重要部分,我不明白为什么noot使用array和regex,但为什么不使用
这是您需要实现的一种代码,但是您的语言描述非常糟糕,不是LL(1),因此如果... ...您遇到的问题是处理一端与另一端之间的差异。可能没有while分隔符,而while结束对您有帮助吗?
这种实现非常繁琐, 我显然不推荐这种事情 !但是挑战很有趣^^
public class MainIndent {
public static enum Tokens {
start("start", 1), end("end", -1), write("write", 0), end_if("end if", -1), read("read", 0), _if("if", 1),
_do("do", 1), _while("while", 1);
private final String keyword;
private final int policy;
Tokens(String keyword, int policy) {
this.keyword = keyword;
this.policy = policy;
}
public int getPolicy() {
return policy;
}
public String getKeyword() {
return keyword;
}
}
public static String parse(String input, String indent) {
String remaining = input;
String parsed = "";
int nbIndent = 0;
int doCount = 0;
while (!remaining.isEmpty()) {
Tokens tokens = getNextToken(remaining);
Tokens nextTokens = getNextToken(remaining.substring(tokens.getKeyword().length()));
int indexOf;
if (nextTokens == null) {
parsed += createIndent(indent, nbIndent+tokens.getPolicy()) + remaining + "\n";
remaining = "";
} else {
if (tokens == Tokens.end_if && (nextTokens == Tokens.end || nextTokens == Tokens.end_if)) {
indexOf = tokens.getKeyword().length()
+ remaining.substring(tokens.getKeyword().length()).indexOf(nextTokens.getKeyword());
} else {
indexOf = remaining.indexOf(nextTokens.getKeyword());
}
int lastIndent = nbIndent;
if (tokens == Tokens._do) {
doCount++;
nbIndent++;
} else if (tokens == Tokens._while && doCount > 0) {
doCount--;
nbIndent--;
lastIndent--;
} else {
if (tokens.getPolicy() < 0) {
lastIndent--;
}
nbIndent += tokens.getPolicy();
}
parsed += createIndent(indent, lastIndent) + remaining.substring(0, indexOf) + "\n";
remaining = remaining.substring(indexOf).trim();
}
System.out.println(parsed);
System.out.println(remaining);
}
return parsed;
}
private static String createIndent(String indent, int nbIndent) {
String output = "";
for (int i = 0; i < nbIndent; i++) {
output += indent;
}
return output;
}
public static void main(String[] args) {
System.out.println(corrIndent(
" start write \"enter your name\" read name\n write \"enter your age\" read age if age==100 then do write \"you stink\" while age!=100 end if while something if something do something while something end if end "));
}
public static String corrIndent(String pseudocode2) {
return corrIndent(pseudocode2, " ");
}
public static String corrIndent(String pseudocode2, String indent) {
String remainingStringtoParse = clearwhiteSpace(pseudocode2); // this will remove all current indentation
return parse(remainingStringtoParse, indent);
}
private static Tokens getNextToken(String input2) {
int startIndex = input2.indexOf(Tokens.start.getKeyword());
startIndex = startIndex == -1 ? input2.length() : startIndex;
int writeIndex = input2.indexOf(Tokens.write.getKeyword());
writeIndex = writeIndex == -1 ? input2.length() : writeIndex;
int readIndex = input2.indexOf(Tokens.read.getKeyword());
readIndex = readIndex == -1 ? input2.length() : readIndex;
int ifIndex = input2.indexOf(Tokens._if.getKeyword());
ifIndex = ifIndex == -1 ? input2.length() : ifIndex;
int doIndex = input2.indexOf(Tokens._do.getKeyword());
doIndex = doIndex == -1 ? input2.length() : doIndex;
int whileIndex = input2.indexOf(Tokens._while.getKeyword());
whileIndex = whileIndex == -1 ? input2.length() : whileIndex;
int endIndex = input2.indexOf(Tokens.end.getKeyword());
endIndex = endIndex == -1 ? input2.length() : endIndex;
int endifIndex = input2.indexOf(Tokens.end_if.getKeyword());
endifIndex = endifIndex == -1 ? input2.length() : endifIndex;
if (startIndex < endIndex && startIndex < endifIndex && startIndex < writeIndex && startIndex < readIndex
&& startIndex < ifIndex && startIndex < doIndex && startIndex < whileIndex) {
return Tokens.start;
} else if (writeIndex < readIndex && writeIndex < ifIndex && writeIndex < doIndex && writeIndex < whileIndex
&& writeIndex < endIndex && writeIndex < endifIndex) {
return Tokens.write;
} else if (readIndex < ifIndex && readIndex < doIndex && readIndex < whileIndex && readIndex < endIndex
&& readIndex < endifIndex) {
return Tokens.read;
} else if (ifIndex < doIndex && ifIndex < whileIndex && ifIndex < endIndex && ifIndex < endifIndex) {
return Tokens._if;
} else if (doIndex < whileIndex && doIndex < endIndex && doIndex < endifIndex) {
return Tokens._do;
} else if (whileIndex < endIndex && whileIndex < endifIndex) {
return Tokens._while;
} else if (endIndex < endifIndex) {
return Tokens.end;
} else if (endifIndex != input2.length()) {
return Tokens.end_if;
} else {
return null;
}
}
private static String clearwhiteSpace(String pseudocode) {
String remainingStringtoParse = pseudocode;
String parsedString = "";
while (remainingStringtoParse.length() > 0) {
remainingStringtoParse = removeHeadWhiteSpace(remainingStringtoParse);
int nextWhiteSpaceIndex = getNextWhiteSpaceIndex(remainingStringtoParse);
parsedString += remainingStringtoParse.substring(0,
nextWhiteSpaceIndex == -1 ? remainingStringtoParse.length() : nextWhiteSpaceIndex)
+ (nextWhiteSpaceIndex == -1 ? "" : " ");
remainingStringtoParse = nextWhiteSpaceIndex == -1 ? ""
: remainingStringtoParse.substring(nextWhiteSpaceIndex);
}
return parsedString;
}
private static int getNextWhiteSpaceIndex(String remainingStringtoParse) {
int whitespace = 0;
while (remainingStringtoParse.length() > whitespace
&& !isWhiteSpace(remainingStringtoParse.charAt(whitespace))) {
whitespace++;
}
return remainingStringtoParse.length() == whitespace ? -1 : whitespace;
}
private static String removeHeadWhiteSpace(String pseudocode) {
int whitespace = 0;
while (pseudocode.length() > whitespace && isWhiteSpace(pseudocode.charAt(whitespace))) {
whitespace++;
}
return pseudocode.length() == whitespace ? "" : pseudocode.substring(whitespace);
}
private static boolean isWhiteSpace(char charAt) {
return Character.isWhitespace(charAt);
}
}
答案 2 :(得分:0)
如果无法使用数组或正则表达式,则必须使用if语句。
您可以做类似的事情
$document = (openfile c:\test\document)
$indentVariable = 0
foreach $line in $document; do
if $line starts with "if" OR "end if" OR "while" OR "end while";
if $line starts with "if"
$indentVariable = $indentVariable + 1
indent $line $indentVariable tabs
$indentVariable = $indentVariable + 1
elseif $line starts with "end if"
$indentVariable = $indentVariable - 2
indent $line $indentVariable tabs
elseif $line starts with "while"
$indentVariable = $indentVariable + 1
indent $line $indentVariable tabs
$indentVariable = $indentVariable + 1
elseif $line starts with "end while"
indentVariable = $indentVariable - 2
indent $line $indentVariable tabs
end if
else
indent $line $indentVariable tabs
end if
end foreach
您将需要添加所有类型的进一步缩进的单词。这就是为什么解决方案通常涉及数组等的原因。
此答案基于“伪代码”,与所有与Java相关的东西都不是。
您也可以像第一个if语句一样最小化它。在if检查中使用非真实的“数组” 像
$document = (openfile c:\test\document)
$indentVariable = 0
foreach $line in $document; do
if $line starts with "if" OR "while"
$indentVariable = $indentVariable + 1
indent $line $indentVariable tabs
$indentVariable = $indentVariable + 1
elseif $line starts with "end if" OR "end while"
$indentVariable = $indentVariable - 2
indent $line $indentVariable tabs
else
indent $line $indentVariable tabs
end if
end foreach