我想为我正在开发的代码生成器提供一些模板。课程的典型模式是:
public ${class_type} ${class_name} extends ${super_class} implements ${interfaces} {
${class_body}
}
问题是super_class是空白还是接口。我用空字符串替换extends $ {super_class}。但我得到额外的空间。所以没有super_class和接口的类最终会像:
public class Foo { //see the extra spaces before {?
${class_body}
}
我知道我可以用单个替换多个空格,但有没有更好的方法?
编辑: 我收到了一些很好的答案,但它没有解决这个问题。我无法指定模板,用户会设置它。否则,有什么意义呢?如果他们愿意怎么办:
public ${class_type} ${class_name} extends ${super_class}
implements ${interfaces} {
${class_body}
}
我想我总是可以删除extends ${super_class}
和之间的所有空格
implements ${interfaces}
当任何一个空白时。它仍然不会很完美,但会更好。
答案 0 :(得分:2)
在字符串“extends $ {super_class}”等中包含前面的空格,所以当你插入一个空字符串时,它根本不会产生空格。
编辑:显然,除了上面的修复,你应该删除字符串之间的空格。
答案 1 :(得分:2)
两个选项:
一个:更改模板:
public ${class_type} ${class_name}${super_block}${interfaces_block} {
${class_body}
}
...并始终替换${super_block}
和${interfaces_block}
- 使用“extends SuperClass”(注意前面的空格但不是末尾)或使用空白字符串。 (同样,接口块将是“实现Foo”[再次是前面的空格]或空白。)
两个:确保在替换时包含前面的空格(编辑:Amir suggested)。但是当你处理像super和interfaces这样的多个块时,这将变得棘手。
(旁注:你引用的模板在开始{
之前的接口位之后有两个空格,这会导致问题。)
答案 2 :(得分:1)
只需在替换模式中包含前面的空格,即_extends_${super_class}
和_implements_${interfaces}
可以替换为空字符串(我使用下划线使其更明确)。
...${class_name}_extends_${super_class}_implements_${interfaces}_{
\_____________________/\_______________________/
optional optional
考虑问题的一种方法是将空间视为它是一个分隔符。类似地,你的问题是这样的:
您可以按该顺序显示A
,B
和C
,但B
和C
是可选的。您希望将它们列为元组,即由(
和)
包围,由,
分隔。也就是说,这些都是有效的元组:
(A,B,C)
(A,B)
(A,C)
(A)
现在更明显的是,您可以将前面的逗号附加到B
和C
。也就是说,元组由4个(A
+ ,B
+ ,C
+ )
组成,中间两个是可选的 - 这样你就不会得到任何额外的分隔符。
注意:由于原因包括简化代码生成,一些语法允许在可变长度列表式句子的末尾使用尾随逗号。例如,在Java中,这是一个有效的数组初始值设定项:
int[] arr = new int[] { 1, 2, }
^
perfectly okay!
对于这些类型的语法,在每个部分之后附加分隔符更有意义。你可以使你的代码生成更复杂,以便它不会产生尾随逗号(也许是因为你只是不喜欢看到一个),但是许多语法确实允许它们证明使用这种简化是合理的。 “快捷方式”。
答案 3 :(得分:0)
如果您想要更强大的解决方案,可以使用an existing template engine或velocity等freemarker。
答案 4 :(得分:0)
我会添加一些方法来表示选项:
public ${class_type} ${class_name} [extends ${super_class} ][implements ${interfaces} ]{
${class_body}
}
因此,如果用户没有指定继承关系,我甚至不会包含空格,而不是删除空格。
答案 5 :(得分:0)
一个好方法是编写一个空白字符串的空白字符串,然后将空格吞噬到下一个关键字。方法签名将是:
void blankKeyword(String content, String keyword, String next);
写起来应该不会太难。