Differencebetween a Property and a Variable in Swift

What is the difference between a property and a variable in Swift?

Local variables are just things that you work with. You have full control over these, and if you change a variable in a function, nothing outside of your function is ever gonna know. If I write a framework and you use it, and I decide to change something about a function's local variables, your app that uses my framework will keep working just as if nothing changed.

Classes, on the other hand, describe a contract. When you use a class, you have access to everything they publicly advertise. This means that if I write a framework and you use it, if I ever change or remove a public member on a class, your code will break if you were previously using that member.

For this reason, in many languages, it's bad practice to mark instance variables as public. Instance variables having no logic attached, if I want at some point to trigger something when a field is changed or if I want to remove the field entirely (and instead report a value in a sub-object or something), then I'm stuck with changing the public contract (turning the field in a pair of get/set methods, for instance), and possibly breaking your code.

Swift makes properties an indirection for this reason. Swift properties can be treated as dumb values for the most part, but if you ever need to change from a stored value to a computed value or something, you can do it without changing your class's interface. That way, you don't break existing code that relies on the property.

Difference between variables

The second variable var b is declared as a stored property:

In its simplest form, a stored property is a constant or variable that
is stored as part of an instance of a particular class or structure.
Stored properties can be either variable stored properties (introduced
by the var keyword) or constant stored properties (introduced by the
let keyword).

You could consider it as the default way for declaring properties.


The first variable var a is declared as a computed property:

In addition to stored properties, classes, structures, and
enumerations can define computed properties, which do not actually
store a value. Instead, they provide a getter and an optional setter
to retrieve and set other properties and values indirectly.

You should declare a computed property when you need to edit the value of a stored property or even getting a new type based on another stored property.

Example:

struct MyStruct {
// stored properties
var var1: Int
var var2: Int

// comupted properties
var multiplication: Int {
return var1 * var2
}

var result: String {
return "result is: \(multiplication)"
}
}

Keep in mind that computed properties do not store the value, instead it just acts like a regular function that returns a value of a type.

Also, you could treat the computed property as a getter-setter for your -private- stored properties, example:

struct AccessControlStruct {
private var stored: String

var computed: String {
get {
return stored
}

set {
stored = newValue.trimmingCharacters(in: .whitespaces)
}
}
}

Since stored declared as private, the only way is to access from out of the structure scope is by setting/getting its value by talking to computed. Obviously, you could any desired edit to the value before setting/getting it to/from stored, as an example, I am letting the newValue string of the computed to be trimmed before setting it to stored, it is also possible to edit the value before getting it.


Reference:

For more information, I would suggest to review:

The Swift Programming Language - Properties.

difference between a computed property and setting a function to a variable in Swift

The code in the computed property gets executed every time you reference that variable. The code in the property initialized by a closure is only executed once, during initialization.

Difference between properties and variables in iOS header file?

Defining the variables in the brackets simply declares them instance variables.

Declaring (and synthesizing) a property generates getters and setters for the instance variable, according to the criteria within the parenthesis. This is particularly important in Objective-C because it is often by way of getters and setters that memory is managed (e.g., when a value is assigned to an ivar, it is by way of the setter that the object assigned is retained and ultimately released). Beyond a memory management strategy, the practice also promotes encapsulation and reduces the amount of trivial code that would otherwise be required.

It is very common to declare an ivar in brackets and then an associated property (as in your example), but that isn't strictly necessary. Defining the property and synthesizing is all that's required, because synthesizing the property implicitly also creates an ivar.

The approach currently suggested by Apple (in templates) is:

Define property in header file, e.g.:

@property (assign, readonly) gameCenter;

Then synthesize & declare ivar in implementation:

@synthesize gameCenter = __gameCenter;

The last line synthesizes the gameCenter property and asserts that whatever value is assigned to the property will be stored in the __gameCenter ivar. Again, this isn't necessary, but by defining the ivar next to the synthesizer, you are reducing the locations where you have to type the name of the ivar while still explicitly naming it.

Is there a difference between an instance variable and a property in Objective-c?

A property is a more abstract concept. An instance variable is literally just a storage slot, like a slot in a struct. Normally other objects are never supposed to access them directly. A property, on the other hand, is an attribute of your object that can be accessed (it sounds vague and it's supposed to). Usually a property will return or set an instance variable, but it could use data from several or none at all. For example:

@interface Person : NSObject {
NSString *name;
}

@property(copy) NSString *name;
@property(copy) NSString *firstName;
@property(copy) NSString *lastName;
@end

@implementation Person
@synthesize name;

- (NSString *)firstName {
[[name componentsSeparatedByString:@" "] objectAtIndex:0];
}
- (NSString *)lastName {
[[name componentsSeparatedByString:@" "] lastObject];
}
- (NSString *)setFirstName:(NSString *)newName {
NSArray *nameArray = [name componentsSeparatedByString:@" "];
NSArray *newNameArray [[NSArray arrayWithObjects:newName, nil] arrayByAddingObjectsFromArray:[nameArray subarrayWithRange:NSMakeRange(1, [nameArray size]-1)]];
self.name = [newNameArray componentsJoinedByString:@" "];
}
- (NSString *)setLastName:(NSString *)newName {
NSArray *nameArray = [name componentsSeparatedByString:@" "];
NSArray *newNameArray [[nameArray subarrayWithRange:NSMakeRange(0, [nameArray size]-2)] arrayByAddingObjectsFromArray:[NSArray arrayWithObjects:newName, nil]];
self.name = [newNameArray componentsJoinedByString:@" "];
}
@end

(Note: The above code is buggy in that it assumes the name already exists and has at least two components (e.g. "Bill Gates" rather than just "Gates"). I felt that fixing those assumptions would make the actual point of the code less clear, so I'm just pointing it out here so nobody innocently repeats those mistakes.)

difference between two types of variable declarations?

TLDR: One is a function, one is a String

var name: String = "Name" is a "regular" variable assignment. You create a var of type String with the identifier name and assign it the value "Name".

var name: String = {return "Name"} won't compile. You're creating a var of type String but then instead of assigning it a string you're assigning it a function. The curly braces indicate a function.

So...

var name = "Name"
print(name)
  1. Creates a variable name with the value name.
  2. Prints the value of variable name [expected output Name]

Whereas

var name = {return "Name"}
print(name)
  1. Creates a variable name with the value of {return "Name"}
  2. Prints that to the console [expected output (Function)]

However

var name = {return "Name"}
print(name())
  1. Creates a variable name with the value of {return "Name"}
  2. Evaluates that function and prints the result [expected output Name]

Therefore

var sum = {return 1+2}
print(sum())
  1. Creates a variable sum with the value of {return 1+2}
  2. Evaluates that function and prints the result [expected output 3]

One last note-- you used single quotes (') but you should declare strings with double quotes (").



Related Topics



Leave a reply



Submit