Static vs Class in Swift: What to Choose for Your Code?

Online Python Trainer for Beginners

Learn Python easily without overwhelming theory. Solve practical tasks with automatic checking, get hints in Russian, and write code directly in your browser — no installation required.

Start Course

Introduction: The Eternal Debate of static and class in Swift

\n

If you've ever written in Swift, you've surely encountered a situation: you need to create a method or variable that belongs to the type itself, not to its instance. And here a dilemma arises — should you use the keyword static or class? On Stack Overflow, this question has gathered thousands of views, and for good reason: the difference is subtle but critically important for proper application architecture design.

\n

In this tutorial, we will once and for all figure out how static and class differ in Swift, when to use which, and how to avoid pitfalls with inheritance. Let's go!

\n\n

What are Type Properties and Methods?

\n

Before diving into the details, let's recall the basics. In Swift, every class, structure, or enumeration has two kinds of members:

\n
    \n
  • Instance — belong to a specific object. To use them, you need to create an instance: let obj = MyClass().
  • \n
  • Type — belong to the type itself. They are called via the type name: MyClass.someMethod().
  • \n
\n

To create type properties and methods in Swift, the keywords static and class are used. And this is where the interesting part begins.

\n\n

Static: Strict and Immutable

\n

The keyword static is your reliable friend when you want to create a property or method that cannot be overridden in a subclass. It works the same for classes, structures, and enumerations.

\n

Let's look at an example. Imagine we are writing a student tracking application and want to store the total count of created objects:

\n\n
class Student {\n    static var totalCount = 0\n    \n    let name: String\n    \n    init(name: String) {\n        self.name = name\n        Student.totalCount += 1\n    }\n    \n    static func printTotal() {\n        print("Total students: \\(totalCount)")\n    }\n}\n\nlet s1 = Student(name: "Ivan")\nlet s2 = Student(name: "Maria")\nStudent.printTotal() // Prints: Total students: 2
\n\n

Notice: we access totalCount and printTotal() through the class name Student, not through an instance. This is convenient for counters, default configurations, or data caching.

\n\n

Static in Structures and Enumerations

\n

In structures and enumerations, static is the only way to declare type members. For example:

\n\n
enum HTTPMethod {\n    case get\n    case post\n    case put\n    \n    static let defaultMethod: HTTPMethod = .get\n}\n\nstruct AppConfig {\n    static let apiURL = "https://api.example.com"\n    static let timeout: Double = 30.0\n}
\n\n

Here static works perfectly because structures and enumerations do not support inheritance, and therefore overriding is not needed.

\n\n

Class: Inheritance Flexibility

\n

The keyword class, on the other hand, is a tool for those working with classes (and only them) who want to allow subclasses to override methods or properties. class cannot be used in structures or enumerations.

\n

Suppose we have a base class Vehicle and we want each subclass to be able to provide its own version of a description:

\n\n
class Vehicle {\n    class func description() -> String {\n        return "This is a vehicle"\n    }\n}\n\nclass Car: Vehicle {\n    override class func description() -> String {\n        return "This is a car"\n    }\n}\n\nclass Bicycle: Vehicle {\n    override class func description() -> String {\n        return "This is a bicycle"\n    }\n}\n\nprint(Vehicle.description()) // This is a vehicle\nprint(Car.description())     // This is a car\nprint(Bicycle.description()) // This is a bicy                

Blogs

Book Recommendations