Java 根据下一个单词在一行中查找一个单词
我有一个文件,这是文件的一部分。所有行中的常用词都是PIC,我可以找到PIC的索引。我试图提取每一行的描述。在这里我如何提取单词PIC之前的单词Java 根据下一个单词在一行中查找一个单词,java,cobol,Java,Cobol,我有一个文件,这是文件的一部分。所有行中的常用词都是PIC,我可以找到PIC的索引。我试图提取每一行的描述。在这里我如何提取单词PIC之前的单词 15 EXTR-SITE PIC X. 05 EXTR-DBA PIC X. TE0305* 05 EXTR-BRANCH PI
15 EXTR-SITE PIC X.
05 EXTR-DBA PIC X.
TE0305* 05 EXTR-BRANCH PIC X(05).
TE0305* 05 EXTR-NUMBER PIC X(06).
TE0305 05 FILLER PIC X(11).
CW0104 10 EXTR-TEXT6 PIC X(67).
CW0104 10 EXTR-TEXT7 PIC X(67).
CW0104* 05 FILLER PIC X(567).
我必须得到如下结果
EXTR-SITE
EXTR-DBA
EXTR-NUMBER
-------
FILLER
在“PIC”之前我能用什么表达法找到这个词吗
下面是我获取包含“PIC”的行的代码:
int wordStartIndex = line.indexOf("PIC");
int wordEndIndex = line.indexOf(".");
if ((wordStartIndex > -1) && (wordEndIndex >= wordStartIndex)) {
System.out.println(line); }
您可以像这样尝试正则表达式:
public static void main(String[] args) {
String s = "15 EXTR-SITE PIC X.";
System.out.println(s.replaceAll("(.*?\\s+)+(.*?)(?=\\s+PIC).*", "$1"));
}
O/p:
说明:
(.*?\\s+)+(.*?)(?=\\s+PIC).*", "$1") :
(.*?\\s+)+ --> Find one or more groups of "anything" which is followed by a space.
(.*?)(?=\\s+PIC) -->find a group of "any set of characters" which are followed by a space and the word "PIC".
.* --> Select everything after PIC.
$1 --> the contents of the actual String with the first captured group i.e, data between `()`.
PS:这适用于所有当前输入:p//让“行”成为所有行的数组
//let 'lines' be an array of all your lines
//with one complete line as string per element
for(String line : lines){
String[] splitted = line.split(" ");
for(int i = 0; i < splitted.length; i++){
if(splitted[i].equals("PIC") && i > 0) System.out.println(splitted[i-1]);
}
}
//每个元素有一个完整的字符串行
对于(字符串行:行){
String[]splitted=line.split(“”);
对于(int i=0;i0)System.out.println(拆分的[i-1]);
}
}
请注意,我还没有测试这段代码(但几分钟后就会测试)。但是,现在应该清楚一般的方法。尝试使用
String.split(\\s+”)
。此方法将原始字符串拆分为字符串数组(string[]
)。然后,使用数组.asList(…)
可以将数组转换为列表
,这样就可以使用索引
搜索特定对象
以下是可能的解决方案的摘录:
String words = "TE0305* 05 EXTR-BRANCH PIC X(05).";
List<String> list = Arrays.asList(words.split("\\s+"));
int index = list.indexOf("PIC");
// Prints EXTR-BRANCH
System.out.println(index > 0 ? list.get(index - 1) : ""); // Added a guard
stringwords=“TE0305*05外部分支PIC X(05)。”;
列表=数组.asList(words.split(\\s+));
int index=list.indexOf(“PIC”);
//输出分支
System.out.println(索引>0?list.get(索引-1):“”);//增加了一名警卫
在我看来,这段代码让Java为您工作,而不是相反。它简洁易懂,更易于维护
我认为您需要在处理此任务之前了解更多关于COBOL的信息
列1-6可以包含序列号,可以为空,也可以包含任何内容。如果您试图解析COBOL代码,则需要忽略第1-6列
第7列称为指示器区域。它可以是空的,或者包含表示注释的*
,或者包含表示该行是前一个非空/非注释行的延续的-
,或者包含表示调试行的D
第73-80列可能包含另一个序列号、空白或任何内容,必须忽略
如果您的COBOL源代码是“自由格式”,情况可能会有所不同,但事实并非如此
从注释行中提取数据毫无意义,因此预期的输出无效。还不清楚您在预期输出中从何处获得虚线
如果您试图解析COBOL源代码,则必须具有有效的COBOL源代码。这是无效的:
TE0305 05 FILLER PIC X(11).
CW0104 10 EXTR-TEXT6 PIC X(67).
CW0104 10 EXTR-TEXT7 PIC X(67).
如果级别编号(05)后面跟有更高级别的编号(两个10),则它是一个组项目。组项目不能有图片
PIC本身也可以写完整,如图片
PIC很容易出现在标识符/数据名(EPIC-CODE)中。理论上可以想象得到
PIC和PICTURE可以出现在注释行中,即使不是注释行代码
您希望用于查找“描述”(即标识符或数据名)的方法存在缺陷
01 the-record.
05 fixed-part-of-record.
10 an-individual-item PIC X.
10 another-item COMP-1.
10 and-another COMP-3 PIC 9(3).
10 PIC X.
05 variable-part-of-record.
10 entry-name OCCURS 10 TIMES.
15 entry-name-client-first-name
PIC X(30).
15 entry-name-client-surname
PIC X(30).
这只是一个简短的例子,不能被视为包罗万象
从中,您的方法将检索
an-individual-item
COMP-3
and two lines of "whatever happens when PIC is the first thing on line"
为了避免这成为一个变色龙问题,你需要用不同的方法问一个新问题(或者自己解决)
根据COBOL源的来源,有更好的方法来处理这个问题。如果源代码是IBM大型机COBOL,那么源代码的源代码应该是编译列表或编译列表中的SYSADATA
从这两个选项中,您可以在特定条件下的特定位置提取标识符/数据名。根本不需要解析
如果你不能得到,那么我建议你寻找等级号,然后找到之后的第一件事。你还有一些工作要做
级别编号可以是一位或两位数字,范围为1-49,再加上66、77、88。一些编译器也有78个。如果你的摘录只是“记录”(很可能),你不会看到77或78。您可能不会看到66(只看到它使用过一次),很可能会看到88,您可能希望也可能不希望将其包含在输出中(取决于您需要它做什么)
使用一位数字作为级别编号而不是明确的拼写填充是相当“新的”(从1985年的标准),很可能您没有这些。但你可以
上述输出应为:
FILLER
FILLER
FILLER
data-name-name-1
data-name-name-2
FILLER
FILLER
FILLER
FILLER
data-name-name-3
data-name-name-4
我不知道你想用这些输出做什么。没有上下文,它就没有太多的意义
您选择的方法可能会处理实际数据(假设您对样本进行了pickle处理,并且得到的是有效代码)
然而,更简单的说法是“如果一行中的第一个单词是一位或两位数字,如果有第二个单词,这就是我们想要的,否则使用FILLER”。当然,请注意前面关于您应该忽略的内容的评论
除非你的来源包含88个等级。因为一系列的值需要第二行是很常见的,如果这些值恰好是数字,一个或两个数字,那么这也不起作用
所以,确定你的来源。如果它是IBM大型机,请尝试从编译中获取输出。那么你的任务真的很简单,而且100%准确
如果你不能做到这一点,那么就彻底了解你的数据。如果您有非常简单的结构,这样您的方法就可以工作,那么从级别编号开始进行操作将更加容易
如果你需要回到这里,请问一个新问题。否则,你就要把那些已经花时间自愿回答你现有问题的人晾干。如果你不是同事
an-individual-item
COMP-3
and two lines of "whatever happens when PIC is the first thing on line"
1.
01.
01 FILLER.
01 data-name-name-1.
01 data-name-name-2 PIC X(80).
5.
05.
05 FILLER.
05 FILLER PIC X.
05 data-name-name-3.
05 data-name-name-4 PIC X.
FILLER
FILLER
FILLER
data-name-name-1
data-name-name-2
FILLER
FILLER
FILLER
FILLER
data-name-name-3
data-name-name-4
JAXBContext jc = JAXBContext.newInstance(Condition.class, Copybook.class, Item.class);
Unmarshaller unmarshaller = jc.createUnmarshaller();
Document doc = Cb2Xml2.convertToXMLDOM(
new File(Code.getFullName("BitOfEverything.cbl").getFile()),
false,
Cb2xmlConstants.USE_STANDARD_COLUMNS);
JAXBElement<Copybook> copybook = unmarshaller.unmarshal(doc, Copybook.class);
List<Item> items = copybook.getValue().getItem();
for (Item item : items) {
Code.printItem(" ", item);
}
public static void printItem(String indent, Item item) {
char[] nc = new char[Math.max(1, 50 - indent.length()
- item.getName().length())];
String picture = item.getPicture();
Arrays.fill(nc, ' ');
if (picture == null) {
picture = "";
}
System.out.println(indent + item.getLevel() + " " + item.getName()
+ new String(nc) + item.getPosition()
+ " " + item.getStorageLength() + "\t" + picture);
List<Item> childItems = item.getItem();
for (Item child : childItems) {
printItem(indent + " ", child);
}
}
01 CompFields 1 5099
03 NumA 1 25 --,---,---,---,---,--9.99
03 NumB 26 3 9V99
03 NumC 29 3 999
03 text 32 20 x(20)
03 NumD 52 3 VPPP999
03 NumE 55 3 999PPP
03 float 58 4
03 double 62 8
03 filler 70 23
05 RBI-REPETITIVE-AREA 70 13
10 RBI-REPEAT 70 13
15 RBI-NUMBER-S96SLS 70 7 S9(06)
15 RBI-NUMBER-S96DISP 77 6 S9(06)
05 SFIELD-SEP 83 10 S9(7)V99