iPhone: Wie erhalte ich aktuelle Millisekunden?

Antworten:

273
[[NSDate date] timeIntervalSince1970];

Es gibt die Anzahl der Sekunden seit der Epoche als Doppel zurück. Ich bin mir fast sicher, dass Sie vom Bruchteil aus auf die Millisekunden zugreifen können.

codelogic
quelle
29
Es bringt niemanden um, es so zu schreiben: NSTimeInterval myInterval = NSDate.timeIntervalSince1970; // all diese Klammern sind wirklich altmodisch, wenn Sie mich fragen.
Pizzaiola Gorgonzola
11
'diese Klammern' sind eine neuere Version der Syntax gemäß stackoverflow.com/q/11474284/209828
Matthew
119
"diese Klammern" sind objektiv-c. Wenn Sie für iOS entwickeln möchten, sollten Sie sich wahrscheinlich mit ihnen vertraut machen.
Ampers4nd
5
Ich verwende diese Methode seit einiger Zeit und habe festgestellt, dass sie einen früheren Wert zurückgeben kann, wenn Sie sie nach einigen Millisekunden aufrufen (z. B. nacheinander aufrufen und möglicherweise nicht mit einer zunehmenden Reihenfolge enden)
Ege Akpinar
5
[NSDate timeIntervalSinceReferenceDate]ist günstiger. (Obwohl es auf eine andere "Epoche" verweist - wenn Sie 1970 wollen, fügen Sie die Konstante hinzu NSTimeIntervalSince1970.)
Hot Licks
311

Wenn Sie dies für das relative Timing verwenden möchten ( zum Beispiel für Spiele oder Animationen), würde ich lieber CACurrentMediaTime () verwenden.

double CurrentTime = CACurrentMediaTime();

Welches ist der empfohlene Weg; NSDateZieht von der vernetzten Synchronisierungsuhr und schluckt gelegentlich, wenn sie erneut mit dem Netzwerk synchronisiert wird.

Es gibt die aktuelle absolute Zeit in Sekunden zurück.


Wenn Sie nur den Dezimalteil möchten (häufig beim Synchronisieren von Animationen verwendet),

let ct = CACurrentMediaTime().truncatingRemainder(dividingBy: 1)
Allan Simonsen
quelle
7
Aber es scheint doppelt so lange zu dauern wie für NSDate dateIntervalSince1970. Ich habe bei 15000 Anrufen 0,065 ms gegenüber 0,033 ms gemessen.
Kay
1
Beachten Sie, dass Sie das Quartz Framework und #import <Quartz / CABase.h> einschließen müssen, um diesen Aufruf durchzuführen.
BadPirate
8
Whoops - das ist Import #import <QuartzCore / CAAnimation.h>
BadPirate
6
Für Xcode-Neulinge (wie mich) bedeutet "Include Quartz Framework" das Hinzufügen zu den Bibliotheken in "Link Binary With Libraries".
Gabe Johnson
3
Wenn jemand dies in Bezug auf SpriteKit sucht, ist die 'aktuelle Zeit' in der Aktualisierungsmethode von SKScene tatsächlich die CACurrentMediaTime ();
Anthony Mattox
92

Ich habe alle anderen Antworten auf einem iPhone 4S und iPad 3 (Release Builds) verglichen. CACurrentMediaTimehat mit geringem Abstand den geringsten Overhead. timeIntervalSince1970ist weitaus langsamer als die anderen, wahrscheinlich aufgrund des NSDateInstanziierungsaufwands, obwohl dies für viele Anwendungsfälle möglicherweise keine Rolle spielt.

Ich würde empfehlen, CACurrentMediaTimewenn Sie den geringsten Overhead wünschen und die Quartz Framework-Abhängigkeit nicht hinzufügen möchten. Oder gettimeofdaywenn Portabilität für Sie Priorität hat.

iPhone 4s

CACurrentMediaTime: 1.33 µs/call
gettimeofday: 1.38 µs/call
[NSDate timeIntervalSinceReferenceDate]: 1.45 µs/call
CFAbsoluteTimeGetCurrent: 1.48 µs/call
[[NSDate date] timeIntervalSince1970]: 4.93 µs/call

iPad 3

CACurrentMediaTime: 1.25 µs/call
gettimeofday: 1.33 µs/call
CFAbsoluteTimeGetCurrent: 1.34 µs/call
[NSDate timeIntervalSinceReferenceDate]: 1.37 µs/call
[[NSDate date] timeIntervalSince1970]: 3.47 µs/call
darrinm
quelle
1
+1, Obwohl dies offensichtlich sehr informativ und hilfreich ist, würde ich es nicht als großartige technische Arbeit bezeichnen, ohne einen Quellcode zu sehen;)
Steven Lu
2
Beachten Sie jedoch dieses Problem: bendodson.com/weblog/2013/01/29/ca-current-media-time Diese Uhr stoppt anscheinend, wenn das Gerät in den Ruhezustand wechselt.
Mojuba
1
Es gibt ein NSTimeIntervalSince1970Makro, das am schnellsten ist.
Ozgur
@ozgur NSTimeIntervalSince1970ist eine Konstante, die die Sekunden zwischen dem 01.01.1970 und dem "Referenzdatum" (dh 01.01.2001) beschreibt. Sie ist also immer gleich 978307200
YourMJK
53

In Swift können wir eine Funktion erstellen und wie folgt vorgehen

func getCurrentMillis()->Int64{
    return  Int64(NSDate().timeIntervalSince1970 * 1000)
}

var currentTime = getCurrentMillis()

Obwohl seine adaequat in Swift 3.0 , aber wir können das ändern und verwenden DateKlasse statt NSDatein 3,0

Swift 3.0

func getCurrentMillis()->Int64 {
    return Int64(Date().timeIntervalSince1970 * 1000)
}

var currentTime = getCurrentMillis()
Rajan Maheshwari
quelle
30

Bisher habe ich gettimeofdayeine gute Lösung für iOS (iPad) gefunden, wenn Sie eine Intervallauswertung durchführen möchten (z. B. Framerate, Timing eines Rendering-Frames ...):

#include <sys/time.h>
struct timeval time;
gettimeofday(&time, NULL);
long millis = (time.tv_sec * 1000) + (time.tv_usec / 1000);
Tristan Lorach
quelle
2
Ich mag das auch, da es sehr portabel ist. Beachten Sie, dass Sie je nach Betriebssystem möglicherweise "long long" anstelle von "long" verwenden und time.tv_sec ebenfalls in "long long" umwandeln müssen, bevor Sie den Rest der Berechnung durchführen.
AbePralle
statische vorzeichenlose lange getMStime (void) {struct timeval time; gettimeofday (& time, NULL); return (time.tv_sec * 1000) + (time.tv_usec / 1000); }
David H
Interessanterweise funktioniert dies gut auf meinem iPhone 5S und Mac, gibt aber auf einem iPad 3 einen falschen Wert zurück.
Hyndrix
Um negative Zahlen zu vermeiden, musste ich vor der Mathematik Folgendes tun: int64_t result = ((int64_t) tv.tv_sec * 1000) + ((int64_t) tv.tv_usec / 1000);
Jason Gilbert
es Rückkehrzeit in -ve
Shauket Sheikh
22

Um Millisekunden für das aktuelle Datum zu erhalten.

Swift 4+:

func currentTimeInMilliSeconds()-> Int
    {
        let currentDate = Date()
        let since1970 = currentDate.timeIntervalSince1970
        return Int(since1970 * 1000)
    }
Rajesh Loganathan
quelle
18

Swift 2

let seconds = NSDate().timeIntervalSince1970
let milliseconds = seconds * 1000.0

Swift 3

let currentTimeInMiliseconds = Date().timeIntervalSince1970.milliseconds
sehr schön
quelle
2
TimeIntervalaka Doublehat keine Millisekunden-Eigenschaft. Date().timeIntervalSince1970 * 1000
Leo Dabus
10

Es kann nützlich sein, sich mit CodeTimestamps vertraut zu machen, die einen Wrapper für machbasierte Timing-Funktionen bieten. Auf diese Weise erhalten Sie Zeitdaten mit einer Auflösung von Nanosekunden - 1000000x genauer als Millisekunden. Ja, millionenfach genauer. (Die Präfixe sind Milli, Micro, Nano, jeweils 1000x genauer als die letzten.) Auch wenn Sie keine CodeTimestamps benötigen, lesen Sie den Code (Open Source), um zu sehen, wie sie mach verwenden, um die Timing-Daten abzurufen. Dies ist nützlich, wenn Sie mehr Präzision benötigen und einen schnelleren Methodenaufruf als den NSDate-Ansatz wünschen.

http://eng.pulse.me/line-by-line-speed-analysis-for-ios-apps/

Tyler
quelle
Und Sie werden wahrscheinlich eine brauchen, -fno-objc-arcwenn Sie ARC verwenden :)
Dan Rosenstark
3
Der von der Seite verlinkte Quellcode ist hier: github.com/tylerneylon/moriarty
Tomas Andrle
8
// Timestamp after converting to milliseconds.

NSString * timeInMS = [NSString stringWithFormat:@"%lld", [@(floor([date timeIntervalSince1970] * 1000)) longLongValue]];
Fatima Arshad
quelle
6

Ich brauchte ein NSNumberObjekt mit dem genauen Ergebnis von [[NSDate date] timeIntervalSince1970]. Da diese Funktion viele Male aufgerufen wurde und ich kein NSDateObjekt erstellen musste , war die Leistung nicht besonders gut.

Versuchen Sie Folgendes, um das Format zu erhalten, das mir die ursprüngliche Funktion gegeben hat:

#include <sys/time.h>
struct timeval tv;
gettimeofday(&tv,NULL);
double perciseTimeStamp = tv.tv_sec + tv.tv_usec * 0.000001;

Welches sollte Ihnen genau das gleiche Ergebnis geben wie [[NSDate date] timeIntervalSince1970]

mmackh
quelle
4

CFAbsoluteTimeGetCurrent ()

Die absolute Zeit wird in Sekunden relativ zum absoluten Referenzdatum vom 1. Januar 2001 00:00:00 GMT gemessen. Ein positiver Wert steht für ein Datum nach dem Stichtag, ein negativer Wert für ein Datum davor. Beispielsweise entspricht die absolute Zeit -32940326 dem 16. Dezember 1999 um 17:54:34 Uhr. Wiederholte Aufrufe dieser Funktion garantieren keine monoton steigenden Ergebnisse. Die Systemzeit kann sich aufgrund der Synchronisation mit externen Zeitreferenzen oder aufgrund einer expliziten Änderung der Uhr durch den Benutzer verringern.

Inder Kumar Rathore
quelle
4

Versuche dies :

NSDate * timestamp = [NSDate dateWithTimeIntervalSince1970:[[NSDate date] timeIntervalSince1970]];

NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
[dateFormatter setDateFormat:@"YYYY-MM-dd HH:mm:ss.SSS"];

NSString *newDateString = [dateFormatter stringFromDate:timestamp];
timestamp = (NSDate*)newDateString;

In diesem Beispiel wird dateWithTimeIntervalSince1970 in Kombination mit dem Formatierer @ "JJJJ-MM-TT HH: mm: ss.SSS" verwendet, der das Datum mit Jahr, Monat, Tag und die Uhrzeit mit Stunden, Minuten, Sekunden und Millisekunden zurückgibt . Siehe das Beispiel: "2015-12-02 04: 43: 15.008". Ich habe den NSString verwendet, um sicherzustellen, dass das Format zuvor geschrieben wurde.

ΩlostA
quelle
4

Dies ist im Grunde die gleiche Antwort wie bei @TristanLorach, die gerade für Swift 3 neu codiert wurde:

   /// Method to get Unix-style time (Java variant), i.e., time since 1970 in milliseconds. This 
   /// copied from here: http://stackoverflow.com/a/24655601/253938 and here:
   /// http://stackoverflow.com/a/7885923/253938
   /// (This should give good performance according to this: 
   ///  http://stackoverflow.com/a/12020300/253938 )
   ///
   /// Note that it is possible that multiple calls to this method and computing the difference may 
   /// occasionally give problematic results, like an apparently negative interval or a major jump 
   /// forward in time. This is because system time occasionally gets updated due to synchronization 
   /// with a time source on the network (maybe "leap second"), or user setting the clock.
   public static func currentTimeMillis() -> Int64 {
      var darwinTime : timeval = timeval(tv_sec: 0, tv_usec: 0)
      gettimeofday(&darwinTime, nil)
      return (Int64(darwinTime.tv_sec) * 1000) + Int64(darwinTime.tv_usec / 1000)
   }
RenniePet
quelle
2
 func currentmicrotimeTimeMillis() -> Int64{
let nowDoublevaluseis = NSDate().timeIntervalSince1970
return Int64(nowDoublevaluseis*1000)

}}

Softlabsindia
quelle
1

Das habe ich für Swift verwendet

var date = NSDate()
let currentTime = Int64(date.timeIntervalSince1970 * 1000)

print("Time in milliseconds is \(currentTime)")

hat diese Website verwendet, um die Richtigkeit zu überprüfen http://currentmillis.com/

DG7
quelle
1
let timeInMiliSecDate = Date()
let timeInMiliSec = Int (timeInMiliSecDate.timeIntervalSince1970 * 1000)
print(timeInMiliSec)
faulerTank
quelle
Bitte fügen Sie Ihrem Code eine Erklärung hinzu, damit andere daraus lernen können - insbesondere, wenn Sie eine Antwort auf eine Frage veröffentlichen, die bereits viele positive Antworten enthält
Nico Haase,
0

[NSDate timeIntervalSinceReferenceDate]ist eine weitere Option, wenn Sie das Quartz-Framework nicht einschließen möchten. Es wird ein Double zurückgegeben, das Sekunden darstellt.

Chris
quelle
0
NSTimeInterval time = ([[NSDate date] timeIntervalSince1970]); //double
long digits = (long)time; //first 10 digits        
int decimalDigits = (int)(fmod(time, 1) * 1000); //3 missing digits
/*** long ***/
long timestamp = (digits * 1000) + decimalDigits;
/*** string ***/
NSString *timestampString = [NSString stringWithFormat:@"%ld%03d",digits ,decimalDigits];
PANKAJ VERMA
quelle