6

I want to define a static variable to hold an NSDate object in Swift 2.2. I've tried the following:

static var interval:NSDate
var static interval:NSDate
var interval:static NSDate

None are working. I've written the same thing in Objective-C with the normal:

static NSString* str

But just isn't working in Swift.

Let me be more clear, I want to use a static interval in the didUpdateLocation method for locationManager so that a function will only happen after five minutes, but the user's location will still be seen in real time. This is how I did it in Objective C

-(void) locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray<CLLocation *> *)locations
{
static NSDate *previous; //<--- This in Swift
static int run = 0;

CLLocation *location = locations.lastObject;

if (run == 0 || [location.timestamp timeIntervalSinceDate:previous] > 10)
{
    [_dbObj insert: location.coordinate.latitude : location.coordinate.longitude : [NSDate date] : location.timestamp];

    previous = location.timestamp;

    run++;
}

MKCoordinateRegion viewRegion = MKCoordinateRegionMakeWithDistance(location.coordinate, 2*1609.34, 2*1609.34);

[[self mapView] setRegion:viewRegion animated:YES];

}

From what I gather, I would need to create a class tat contains this static NSDate variable and instantiate it in the didUpdateLocations method. Yes? Thanks!

Nick D.
  • 69
  • 1
  • 1
  • 5
  • 4
    You can define `static` property within a class using the first syntax. But where are you trying to do this? The Objective-C `static` keyword can be used at different scopes (a global, to make it accessible only to that compilation unit; a local variable within a method implementation) that aren't permitted in Swift. You have to show us _where_ you're trying to do this for us to comment further. – Rob Jul 02 '16 at 20:40
  • 1
    Possible duplicate of [Static properties in Swift](http://stackoverflow.com/questions/26567480/static-properties-in-swift) – ΦXocę 웃 Пepeúpa ツ Jul 02 '16 at 20:43
  • That are function-scoped static vars, and my suggestion should work. – But why don't you make them instance variables of the enclosing class instead? – Martin R Jul 04 '16 at 04:46

2 Answers2

15

In C,

static <type> <name>;

at the file level defines a variable name whose scope is restricted to the same compilation unit (roughly speaking: to the same source file), and the same applies to your Objective-C code

static NSString* str;

In Swift, you achieve the same effect with a private property defined on the file level:

private var date = NSDate()

date is visible only in the same source file, compare Access Control in the Swift blog.


Function scoped static variables are possible in Swift as well, but you have to put them inside a struct. Example:

func foo() -> Int {
    struct StaticVars {
        static var counter = 0
    }
    StaticVars.counter += 1
    return StaticVars.counter
}

print(foo()) // 1
print(foo()) // 2
Martin R
  • 529,903
  • 94
  • 1,240
  • 1,382
  • 2
    Private and static are definitely NOT the same thing. Private only affects scope, i.e., visibility. Static in a C-family language has many different semantics, depending on the context in which it is used. At file scope it's similar to private, at class scope it denotes a class variable vs an instance variable, at subroutine scope it denotes a persistent non-stack based value, etc. – David Berry Jul 02 '16 at 21:47
  • 1
    @DavidBerry: That's why I explicitly said "static on the file level". I did not mention "static on class scope" (nor does the question, as far as I can tell). *"At file scope it's similar to private,"* – that's exactly what I tried to explain. – Martin R Jul 02 '16 at 21:51
  • I guess my point was in agreement with @rob, there's not enough info to answer the question because they say nothing about scope. My assumption was/is actually that they're asking about function scoped... – David Berry Jul 02 '16 at 21:53
  • @DavidBerry: It seems that you were right with your assumption, the question is about function-scoped static variables. I have updated the answer accordingly. – Martin R Jul 04 '16 at 04:49
  • Vehicle().car = "Mercedes", Vehicle().car, giving **Lexus** , but, let vehObj = Vehicle(); vehObj.car, giving **Mercedes** . I don't know why. Whats the diff? Can u Guide me? – McDonal_11 Jul 08 '19 at 07:39
  • @McDonal_11: Every `Vehicle()` call creates a *new instance.* – Martin R Jul 08 '19 at 07:43
  • Can u pls explain clearly? I couldn't find difference. – McDonal_11 Jul 08 '19 at 07:45
  • @McDonal_11: Comments are for clarification about the current question or answer, not for arbitrary discussion. If you have a question then you should post it as a question. Don't forget a [mcve] which clearly demonstrates your problem. – Martin R Jul 08 '19 at 08:08
5

There are two problems here:

  • static or class members are allowed only inside a class, and
  • static members need to be initialized (or be declared optional to be initialized with nil).

Example:

class Foo {
    static var dt : NSDate = NSDate()
    static var optDt : NSDate? = nil
}

Note that the first restriction is not present in Objective-C: you are allowed to have free-standing static variables, in addition to function-scoped static variables.

Sergey Kalinichenko
  • 714,442
  • 84
  • 1,110
  • 1,523