How to compare two NSDates: Which is more recent?

I am trying to achieve a dropBox sync and need to compare the dates of two files. One is on my dropBox account and one is on my iPhone.

I came up with the following, but I get unexpected results. I guess I’m doing something fundamentally wrong when comparing the two dates. I simply used the > < operators, but I guess this is no good as I am comparing two NSDate strings. Here we go:

  • Redrawing UIScrollView contents after every zoom
  • How do I build and install applications on a jailbroken iPhone without being in the iPhone Developer Program?
  • iOS 4.2 - Printing DOC, PPT, XLS, etc. with Apple AirPrint?
  • Uncaught exception: This class is not key value coding-compliant
  • Accessing photos from a specific album from photolibrary
  • iOS7 new update V 7.1(11D167) not compatible in Xcode 5 for development
  • NSLog(@"dB...lastModified: %@", dbObject.lastModifiedDate); 
    NSLog(@"iP...lastModified: %@", [self getDateOfLocalFile:@"NoteBook.txt"]);
    
    if ([dbObject lastModifiedDate] < [self getDateOfLocalFile:@"NoteBook.txt"]) {
        NSLog(@"...db is more up-to-date. Download in progress...");
        [self DBdownload:@"NoteBook.txt"];
        NSLog(@"Download complete.");
    } else {
        NSLog(@"...iP is more up-to-date. Upload in progress...");
        [self DBupload:@"NoteBook.txt"];
        NSLog(@"Upload complete.");
    }
    

    This gave me the following (random & wrong) output:

    2011-05-11 14:20:54.413 NotePage[6918:207] dB...lastModified: 2011-05-11 13:18:25 +0000
    2011-05-11 14:20:54.414 NotePage[6918:207] iP...lastModified: 2011-05-11 13:20:48 +0000
    2011-05-11 14:20:54.415 NotePage[6918:207] ...db is more up-to-date.
    

    or this one which happens to be correct:

    2011-05-11 14:20:25.097 NotePage[6903:207] dB...lastModified: 2011-05-11 13:18:25 +0000
    2011-05-11 14:20:25.098 NotePage[6903:207] iP...lastModified: 2011-05-11 13:19:45 +0000
    2011-05-11 14:20:25.099 NotePage[6903:207] ...iP is more up-to-date.
    

    13 Solutions Collect From Internet About “How to compare two NSDates: Which is more recent?”

    Let’s assume two dates:

    NSDate *date1;
    NSDate *date2;
    

    Then the following comparison will tell which is earlier/later/same:

    if ([date1 compare:date2] == NSOrderedDescending) {
        NSLog(@"date1 is later than date2");
    } else if ([date1 compare:date2] == NSOrderedAscending) {
        NSLog(@"date1 is earlier than date2");
    } else {
        NSLog(@"dates are the same");
    }
    

    Please refer to the NSDate class documentation for more details.

    Late to the party, but another easy way of comparing NSDate objects is to convert them into primitive types which allows for easy use of ‘>’ ‘<‘ ‘==’ etc

    eg.

    if ([dateA timeIntervalSinceReferenceDate] > [dateB timeIntervalSinceReferenceDate]) {
        //do stuff
    }
    

    timeIntervalSinceReferenceDate converts the date into seconds since the reference date (1 January 2001, GMT). As timeIntervalSinceReferenceDate returns a NSTimeInterval (which is a double typedef), we can use primitive comparators.

    NSDate has a compare function.

    compare: Returns an NSComparisonResult value that indicates the temporal ordering of the receiver and another given date.

    (NSComparisonResult)compare:(NSDate *)anotherDate
    

    Parameters: anotherDate
    The date with which to compare the receiver.
    This value must not be nil. If the value is nil, the behavior is undefined and may change in future versions of Mac OS X.

    Return Value:

    • If the receiver and anotherDate are exactly equal to each other, NSOrderedSame
    • If the receiver is later in time than anotherDate, NSOrderedDescending
    • If the receiver is earlier in time than anotherDate, NSOrderedAscending.

    In Swift, you can overload existing operators:

    func > (lhs: NSDate, rhs: NSDate) -> Bool {
        return lhs.timeIntervalSinceReferenceDate > rhs.timeIntervalSinceReferenceDate
    }
    
    func < (lhs: NSDate, rhs: NSDate) -> Bool {
        return lhs.timeIntervalSinceReferenceDate < rhs.timeIntervalSinceReferenceDate
    }
    

    Then, you can compare NSDates directly with <, >, and == (already supported).

    You want to use the NSDate compare:, laterDate:, earlierDate:, or isEqualToDate: methods. Using the < and > operators in this situation is comparing the pointers, not the dates

    - (NSDate *)earlierDate:(NSDate *)anotherDate
    

    This returns the earlier of the receiver and anotherDate. If both are same, the receiver is returned.

    Some date utilities, including comparisons IN ENGLISH, which is nice:

    #import <Foundation/Foundation.h>
    
    
    @interface NSDate (Util)
    
    -(BOOL) isLaterThanOrEqualTo:(NSDate*)date;
    -(BOOL) isEarlierThanOrEqualTo:(NSDate*)date;
    -(BOOL) isLaterThan:(NSDate*)date;
    -(BOOL) isEarlierThan:(NSDate*)date;
    - (NSDate*) dateByAddingDays:(int)days;
    
    @end
    

    The implementation:

    #import "NSDate+Util.h"
    
    
    @implementation NSDate (Util)
    
    -(BOOL) isLaterThanOrEqualTo:(NSDate*)date {
        return !([self compare:date] == NSOrderedAscending);
    }
    
    -(BOOL) isEarlierThanOrEqualTo:(NSDate*)date {
        return !([self compare:date] == NSOrderedDescending);
    }
    -(BOOL) isLaterThan:(NSDate*)date {
        return ([self compare:date] == NSOrderedDescending);
    
    }
    -(BOOL) isEarlierThan:(NSDate*)date {
        return ([self compare:date] == NSOrderedAscending);
    }
    
    - (NSDate *) dateByAddingDays:(int)days {
        NSDate *retVal;
        NSDateComponents *components = [[NSDateComponents alloc] init];
        [components setDay:days];
    
        NSCalendar *gregorian = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];
        retVal = [gregorian dateByAddingComponents:components toDate:self options:0];
        return retVal;
    }
    
    @end
    

    You should use :

    - (NSComparisonResult)compare:(NSDate *)anotherDate
    

    to compare dates. There is no operator overloading in objective C.

    I have encounter almost same situation, but in my case I’m checking if number of days difference

    NSCalendar *cal = [NSCalendar currentCalendar];
    NSDateComponents *compDate = [cal components:NSDayCalendarUnit fromDate:fDate toDate:tDate options:0];
    int numbersOfDaysDiff = [compDate day]+1; // do what ever comparison logic with this int.
    

    Useful when you need to compare NSDate in Days/Month/Year unit

    Why don’t you guys use these NSDate compare methods:

    - (NSDate *)earlierDate:(NSDate *)anotherDate;
    - (NSDate *)laterDate:(NSDate *)anotherDate;
    

    You can compare two date by this method also

            switch ([currenttimestr  compare:endtimestr])
            {
                case NSOrderedAscending:
    
                    // dateOne is earlier in time than dateTwo
                    break;
    
                case NSOrderedSame:
    
                    // The dates are the same
                    break;
                case NSOrderedDescending:
    
                    // dateOne is later in time than dateTwo
    
    
                    break;
    
            }
    

    I have tried it hope it works for you

    NSCalendar *gregorian = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];      
    int unitFlags =NSDayCalendarUnit;      
    NSDateFormatter *dateFormatter = [[[NSDateFormatter alloc] init] autorelease];     
    NSDate *myDate; //= [[NSDate alloc] init];     
    [dateFormatter setDateFormat:@"dd-MM-yyyy"];   
    myDate = [dateFormatter dateFromString:self.strPrevioisDate];     
    NSDateComponents *comps = [gregorian components:unitFlags fromDate:myDate toDate:[NSDate date] options:0];   
    NSInteger day=[comps day];
    

    Use this simple function for date comparison

    -(BOOL)dateComparision:(NSDate*)date1 andDate2:(NSDate*)date2{
    
    BOOL isTokonValid;
    
    if ([date1 compare:date2] == NSOrderedDescending) {
        NSLog(@"date1 is later than date2");
        isTokonValid = YES;
    } else if ([date1 compare:date2] == NSOrderedAscending) {
        NSLog(@"date1 is earlier than date2");
        isTokonValid = NO;
    } else {
        isTokonValid = NO;
        NSLog(@"dates are the same");
    }
    
    return isTokonValid;}