0

我有一个文件,其中包含许多电影标题以及它们的年份、5 星评分和长度。我正在尝试读取文件并将标题、年份、评级和长度存储为变量。我遇到的问题是在我检索年份的代码中。代码可以编译,但在运行时会抛出 NumberFormatException 异常,因为它会播放一部多年的电影(例如,它被列为 2006-2009)。这是我的代码。

while((line = bufferedReader.readLine()) != null) {
                //System.out.println(line);
                for(int i = 0; i < line.length(); i++)
                {

                    if(line.charAt(i) == ')' || line.charAt(i) == '-')//get year
                    {
                        yr = line.substring(yearStart,i);
                        year = Integer.parseInt(yr);
                    }

                }
                System.out.println(year);

            }

不应该line.charAt(i) == '-'在我的 if 语句中处理这个问题吗?

编辑:下面的代码是 yearStart 的来源。

if(line.charAt(i) == '(')//get title
                    {
                        title = line.substring(0,i);
                        yearStart = i+1;
                    }

该文件的格式如下: title (year) | rating, length 对不起,我最初应该包含该文件。

编辑#2:这是文件的一部分的示例,如果有帮助的话

!Women Art Revolution (2010) |   3 stars, 1hr 22m
#1 Cheerleader Camp (2010) |   3 stars, 1hr 35m
$5 a Day (2008) |   3.4 stars, 1hr 37m
'night, Mother (1986) |   3.7 stars, 1hr 36m
'Til Death (2006-2009) |   3.7 stars, 4 Seasons//This is the one that causes the error
@Suicide Room (2011) |   3.4 stars, 1hr 51m
... And God Spoke (1993) |   2.8 stars, 1hr 22m
4

4 回答 4

2

找到年份后会发生什么?循环将一直运行到行尾,每次找到 a)或 a时都会尝试将事物解析为数字-

找到年份后,也许您应该退出循环。

                if(line.charAt(i) == ')' || line.charAt(i) == '-')//get year
                {
                    yr = line.substring(yearStart,i);
                    year = Integer.parseInt(yr);
                    break; // year found, no point in looping more
                }

或者也许您应该重置yearStart索引以便可以解析第二年。

                if (line.charAt(i) == '-')
                {
                    // parse first year
                    yr = line.substring(yearStart,i);
                    year = Integer.parseInt(yr);
                    yearStart = i + 1; // reset to parse second year
                }
                else if (line.charAt(i) == ')')
                {
                    yr = line.substring(yearStart,i);
                    year = Integer.parseInt(yr);
                    break; // year found
                }
于 2013-11-09T20:41:52.443 回答
0

找到第一年之后,yearStart仍然是第一年的索引。因此,当您尝试获取 asubString时,它仍然是(2006-2009)- Automatic NumberFormatException,无法解析-.

您应该yearStart在发现第一年之后更改:

for(int i = 0; i < line.length(); i++)
{

    if(line.charAt(i) == ')' || line.charAt(i) == '-')//get year
    {
          yr = line.substring(yearStart,i);
          year = Integer.parseInt(yr);
          yearStart = i + 1;
    }

}
于 2013-11-09T20:48:44.307 回答
0

该条件if(line.charAt(i) == ')' || line.charAt(i) == '-')在您的循环中两次成立。首先,当连字符匹配时,然后,当右括号匹配时。在您的示例中,第一次year分配给2009. 但随后,循环继续运行,经过几次迭代,您尝试解析"2005-2009"导致 NumberFormatException 的结果。

最直接的解决方案是break;在分配 year 之后循环,因此year只分配一次。也就是说,假设您想要获取间隔的起始值。

一个更清洁的解决方案是完全避免循环,而是明智地使用String.indexOf. 类似的东西(免责声明:未经测试)。

String title;
int year;

while((line = bufferedReader.readLine()) != null) {

    title = line.substring(0, line.indexOf('('));

    int yearStart = line.indexOf('(') + 1;
    int yearEnd;
    if (line.indexOf('-', yearStart) > 0 ) {
        yearEnd = line.indexOf('-', yearStart);
    } else {
        yearEnd = line.indexOf('(', yearEnd);
    }

    int yr = line.substring(yearStart,i);
    year = Integer.parseInt(yr);

    System.out.println(year);
}

最后,更专业的解决方案是使用正则表达式,我知道您可能对此并不熟悉,因此我试图提供一个与您的结构相似的答案。

于 2013-11-09T20:52:50.203 回答
0

将 Intger.parseInt 放入 try/catch 块(类似于下面的块)以查看失败的位置以及如何:

try { 
  year = Integer.parseInt(yr);
} catch (Exception e) {
  throw new RuntimeException(
      "Failed to parse year '" + yr + "' in line '" + line + "'", e);
}

顺便说一句:line.indexOf(')') 返回 '(' 在行中的位置。

于 2013-11-09T20:38:05.783 回答