将NSString转换为NSTimeInterval

4

我尝试使用NSTimeInterval制作倒计时。但我希望能够在不发布更新的情况下更改时间间隔。因此,我尝试从我的网站导入TimeInterval。我已经将NSTimeInterval的数字存储在NSString中,现在想将其转换为NSTimeInterval,以便将其实现到倒计时代码中...

...但是它没有起作用。有什么想法吗?

label.text = string;
double timeInterval = [label.text doubleValue];
NSTimeInterval intervalForTimer = timeInterval;
destinationDate = [[NSDate dateWithTimeIntervalSince1970:intervalForTimer] retain];
timer = [NSTimer scheduledTimerWithTimeInterval:1.0 target:self selector:@selector(updateLabel) userInfo:nil repeats:YES];

编辑:

- (void)updateLabel {

    NSCalendar *calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];
    int units = NSMonthCalendarUnit | NSDayCalendarUnit | NSHourCalendarUnit | NSMinuteCalendarUnit | NSSecondCalendarUnit;
    NSDateComponents *components = [calendar components:units fromDate:[NSDate date] toDate:destinationDate options:0];
    [dateLabel setText:[NSString stringWithFormat:@"%d%c %d%c %d%c %d%c %d%c", [components month], 'm', [components day], 'd', [components minute], 'm', [components second], 's']];

}

我的新代码看起来是这样的:

    NSLog(@"Downloaded file with contents: %@", string);
    double timeInterval = [string doubleValue];
    label.text = [NSString stringWithFormat:@"%d", (int)timeInterval];
    NSTimeInterval intervalForTimer = timeInterval;
    destinationDate = [[NSDate dateWithTimeIntervalSince1970:timeInterval] retain];
    timer = [NSTimer scheduledTimerWithTimeInterval:intervalForTimer target:self selector:@selector(updateLabel) userInfo:nil repeats:YES];

但是dateLabel并没有任何作用...


什么问题?看起来没问题。 - Inder Kumar Rathore
它为什么不工作?您是否验证(通过显示或使用调试器查看)字符串值是否正确传入?您是否验证标签文本是否被正确设置? - Nathan S.
如果我启动应用程序,倒计时本身会输出非常奇怪的结果。我只是使用标签将其转换为NSTimeInterval。 - AmiiQo
3个回答

7

你的URL,http://gymnasium2.ai.ch/~mensa/countdown_timestamp.html,是一个完整的HTML文件。 NSString initWithContentsOfURL:将返回一个包含它所有内容的字符串:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<title>1328633219</title>
</head>

<body>
1328633219
</body>
</html>

这无法转换为double类型;您需要解析HTML,这可能需要很多工作。

更简单的方法是上传一个仅包含数字的简单文件:

1328633219

那么你以上的代码就可以在不做任何更改的情况下获取数字。

然而,以下代码可能会阻止你的代码正常工作:

NSString *string = [[NSString alloc] initWithContentsOfURL:[NSURL URLWithString:@"http://gymnasium2.ai.ch/~mensa/countdown_timestamp.html"]];
label.text = string; // This line
double timeInterval = [label.text doubleValue];

如果labelnil,那么timeInterval将无法正确设置,因为[label.text doubleValue]也会返回nil。你可以尝试使用以下代码代替:
NSString *string = [[NSString alloc] initWithContentsOfURL:[NSURL URLWithString:@"http://gymnasium2.ai.ch/~mensa/countdown_timestamp.html"]];
double timeInterval = string;
label.text = [NSString stringWithFormat:@"%d", (int)timeInterval];

在获取文件之后,放置断点或添加NSLog调用会很有帮助,这样您可以看到发生了什么。

NSString *string = [[NSString alloc] initWithContentsOfURL:[NSURL URLWithString:@"http://gymnasium2.ai.ch/~mensa/countdown_timestamp.html"]];
NSLog(@"Downloaded file with contents: %@", string);

或者,您可以上传一个 plist 文件,并使用类似于 NSDictionary dictionaryWithContentsOfURL:NSArray arrayWithContentsOfURL: 的方法。请参阅属性列表编程指南


我尝试使用txt文件,这应该比html文件更好用,对吧? - AmiiQo
如果你的 txt 文件只包含数字,没有其它任何内容, 那么可以这么做。因为你从 label.text 中获取数字,所以必须确保标签不为空。你可以尝试使用 double timeInterval = [string doubleValue] - mrb
现在它已经下载了正确的文件:"Countdown[1538:f803] Downloaded file with contents: 1354904016",但标签没有显示任何内容... - AmiiQo
听起来你只需要确保标签设置正确。例如,如果你使用了nib/xib,请确保它连接到正确的出口。你可以使用类似NSLog(@"Label is %@", label);这样的东西来查看它是否为nil或其他内容,但由于你现在拥有正确的内容,你应该能够将其转换为NSTimeInterval并进行任何其他操作。 - mrb
它告诉我标签为(null),奇怪的是我把所有东西都连接起来了,就像它该连接的那样。我将dateLabel与xib文件中的标签连接起来,没有其他的。 - AmiiQo
可能是因为你在代码中没有设置dateLabel,而只是label?也许你需要像这样:dateLabel.text = ... - mrb

2
NSTimeInterval timeInterval = [self timeIntervalFromString:@"00:01:40"];
NSLog(@"timeInterval %f", timeInterval);

- (NSTimeInterval)timeIntervalFromString:(NSString *)string {
NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
[dateFormatter setDateFormat:@"HH:mm:ss"];
NSDate *start = [dateFormatter dateFromString:@"00:00:00"];
NSDate *end = [dateFormatter dateFromString:string];
NSTimeInterval interval = [end timeIntervalSinceDate:start];
return interval;
}

输出: 时间间隔 100.000000


如果值为 "66:66:66",则结束值将为 nil 并且 [end timeIntervalSinceDate:start]; 会导致应用程序崩溃。 - ayalcinkaya

1

你是否使用Xcode调试器逐步执行代码,查看哪一行代码出现了意外结果?你从未使用destinationDate,实际上你应该传递以下代码到最后一行:

timer = [NSTimer scheduledTimerWithTimeInterval:intervalForTimer target:self selector:@selector(updateLabel) userInfo:nil repeats:YES];

此外,你获取时间间隔值的地方是一个带有HTML标签的网页。将countdown_timestamp.html更改为countdown_timestamp.txt,并将时间间隔值单独放入其中(例如"2.0"),不要将其包装在HTML中。


我添加了updateLabel,这样你就可以看到我在哪里使用destinationDate... 但它似乎仍然无法与txt文件一起工作。 - AmiiQo
听起来你的IBOutlet出了问题。我敢打赌label是nil。所以任何试图从label.text中取值的代码都将返回零或nil。 - Duncan C

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接