惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

奇客Solidot–传递最新科技情报
奇客Solidot–传递最新科技情报
J
Java Code Geeks
I
InfoQ
V
Visual Studio Blog
M
MIT News - Artificial intelligence
H
Help Net Security
博客园_首页
Blog — PlanetScale
Blog — PlanetScale
F
Fortinet All Blogs
Apple Machine Learning Research
Apple Machine Learning Research
人人都是产品经理
人人都是产品经理
G
Google Developers Blog
A
About on SuperTechFans
腾讯CDC
让小产品的独立变现更简单 - ezindie.com
让小产品的独立变现更简单 - ezindie.com
Last Week in AI
Last Week in AI
小众软件
小众软件
aimingoo的专栏
aimingoo的专栏
罗磊的独立博客
大猫的无限游戏
大猫的无限游戏
Cyber Security Advisories - MS-ISAC
Cyber Security Advisories - MS-ISAC
云风的 BLOG
云风的 BLOG
S
SegmentFault 最新的问题
WordPress大学
WordPress大学

DEV Community

Authentication Security Deep Dive: From Brute Force to Salted Hashing (With Java Examples) Why AI Systems Don’t Fail — They Drift Spilling beans for how i learn for exam😁"Reinforcement Learning Cheat Sheet" I Replaced Chrome with Safari for AI Browser Automation. Here's What Broke (and What Finally Worked) How Python Borrows Other People's Work The $40 Architecture: Processing 1 Billion API Requests with 99.99% Uptime Vibe Coding: A Workflow Guide (From Zero to SaaS) Most webhook security guides protect the wrong side. The scary part is delivery. Headless CMS for TanStack Start: Build a Blog with Cosmic EU Age Verification App "Hacked in 2 Minutes" — What Actually Happened Comfy Cloud’s delete function does not actually remove files Running AI Models on GPU Cloud Servers: A Beginner Guide Event-driven media intelligence with AWS Step Functions and Bedrock I scored 500 AI prompts across 8 quality dimensions — here's what broke How to Call Google Gemini API from Next.js (Free Tier, No Backend Needed) The Portal Protocol: Reclaiming Human Connection in the Age of AI How to Fix Your Team's Scattered Knowledge Problem With a Self-Hosted Forum Intro to tc Cloud Functors: A Graph-First Mental Model for the Modern Cloud Designing Multi-Tenant Backends With Both Ownership and Team Access I Built a Neumorphic CSS Library with 77+ Components — Here's What I Learned PostgreSQL Performance Optimization: Why Connection Pooling Is Critical at Scale Cómo construí un SaaS multi-rubro para gestionar expensas en Argentina con FastAPI + Vue 3 🚀 I Built an Ethical Hacking Scanner Tool – Open Source Project I Replaced /usage and /context in Claude Code With a Single Statusline A Pythonic Way to Handle Emails (IMAP/SMTP) with Auto-Discovery and AI-Ready Design I Collected 8.9 Million Polymarket Price Points — Here's What I Found About How Markets Really Move EcoTrack AI — Carbon Footprint Tracker & Dashboard Everyone's Using AI. No One Agrees How. 5 self-hosted ebook managers worth trying in 2026 Building Your First AI Agent with LangChain: From Chatbot to Autonomous Assistant
Swift Structs — Building Your Own Custom Types 🏗️
Gamya · 2026-06-27 · via DEV Community

So far we've been working with Swift's built-in types — String, Int, Bool, Array. But what if you need a type that doesn't exist yet? What if you want to represent a ninja, or an anime character, or a guild? That's exactly what structs are for. 🍥

A struct lets you create your own custom, complex data type — complete with its own variables and its own functions.


Creating Your First Struct

Here's a simple struct that represents an anime character:

struct AnimeCharacter {
    let name: String
    let show: String
    let powerLevel: Int

    func printSummary() {
        print("\(name) from \(show) — Power Level: \(powerLevel)")
    }
}

Notice a few things:

  • AnimeCharacter starts with a capital letter — that's the Swift convention for all types (String, Int, Bool, and now our own AnimeCharacter)
  • name, show, and powerLevel are properties — variables and constants that belong to the struct
  • printSummary() is a method — a function that belongs to the struct

Now let's create some characters:

let naruto = AnimeCharacter(name: "Naruto", show: "Naruto Shippuden", powerLevel: 9000)
let goku = AnimeCharacter(name: "Goku", show: "Dragon Ball Z", powerLevel: 9001)

print(naruto.name)     // "Naruto"
print(goku.powerLevel) // 9001

naruto.printSummary()  // "Naruto from Naruto Shippuden — Power Level: 9000"
goku.printSummary()    // "Goku from Dragon Ball Z — Power Level: 9001"

Even though both naruto and goku are created from the same AnimeCharacter struct, they are completely separate instances — changing one won't affect the other. When printSummary() is called on naruto, it uses Naruto's data. When called on goku, it uses Goku's data. Swift handles this automatically.


Properties, Methods, and Instances — The Vocabulary

Now that you've seen a struct in action, let's give names to the pieces:

  • Properties — the variables and constants inside a struct (name, show, powerLevel)
  • Methods — the functions inside a struct (printSummary())
  • Instance — a specific copy of a struct (naruto, goku are both instances of AnimeCharacter)
  • Initializer — the special function used to create an instance (AnimeCharacter(name:show:powerLevel:))

That last one is worth slowing down on.


How Initializers Work

When you write AnimeCharacter(name: "Naruto", show: "Naruto Shippuden", powerLevel: 9000), it looks like you're calling a function. You kind of are — Swift silently creates a special function called init() inside every struct, using all the properties as parameters. These two lines are identical:

let naruto = AnimeCharacter(name: "Naruto", show: "Naruto Shippuden", powerLevel: 9000)
let naruto = AnimeCharacter.init(name: "Naruto", show: "Naruto Shippuden", powerLevel: 9000)

You'll almost always use the first version — but now you know what's actually happening behind the scenes.

Swift is also smart about default values. If you give a property a default value, Swift makes it optional in the initializer:

struct Ninja {
    let name: String
    var chakraLevel = 100
}

let kakashi = Ninja(name: "Kakashi")             // uses default chakraLevel of 100
let rock = Ninja(name: "Rock Lee", chakraLevel: 0) // Rock Lee has no chakra 😄


Mutating Properties: The mutating Keyword

Let's say we want our ninja to be able to train and increase their chakra:

struct Ninja {
    let name: String
    var chakraLevel: Int

    func train() {
        chakraLevel += 50  // ❌ This won't work!
        print("\(name) trained hard!")
    }
}

Swift will refuse to build this. Why? Because chakraLevel is a var — it can change — but Swift doesn't know whether the instance of the struct is a var or a let. If you created a let ninja, changing its properties would be wrong.

The solution is to mark any method that changes properties with the mutating keyword:

struct Ninja {
    let name: String
    var chakraLevel: Int

    mutating func train() {
        chakraLevel += 50
        print("\(name) trained hard! Chakra is now \(chakraLevel).")
    }
}

Now it works — but only when the instance is created as a var:

var naruto = Ninja(name: "Naruto", chakraLevel: 100)
naruto.train() // ✅ "Naruto trained hard! Chakra is now 150."

let sasuke = Ninja(name: "Sasuke", chakraLevel: 100)
sasuke.train() // ❌ Error — can't call mutating method on a constant

Two important things to remember about mutating:

  1. Swift takes your word for it — if you mark a method as mutating, Swift will prevent it from being called on constant structs, even if the method doesn't actually change anything
  2. A non-mutating method can't call a mutating one — if you need that, mark both as mutating

Methods vs Functions — What's the Difference?

You might be wondering: if a method is just a function inside a struct, why bother? Why not just use functions for everything?

The key difference is that methods belong to a type — they live inside a struct (or class, or enum). Regular functions float freely in your code.

This matters for two reasons:

1. Methods can access the struct's own properties:

struct Guild {
    let name: String
    var memberCount: Int

    func describe() {
        // Can access 'name' and 'memberCount' directly
        print("\(name) has \(memberCount) members.")
    }
}

A regular function outside the struct couldn't do this without being passed the data explicitly.

2. Methods avoid namespace pollution:

Imagine you write 100 free-floating functions — attack(), defend(), heal(), etc. Those names now mean something everywhere in your code, and you might accidentally conflict with other code using the same names.

But if those functions are methods on a Character struct, they don't conflict with anything — character.attack() is clearly about that character's attack, and item.attack() could mean something completely different on an Item struct.


Structs vs Tuples — Which Should You Use?

You might remember tuples from the functions article — they let you return multiple values at once:

func getCharacterInfo() -> (name: String, powerLevel: Int) {
    return ("Luffy", 8500)
}

A tuple and a struct can hold similar data, so when should you use each?

Think of a tuple as an anonymous struct — it's great for one-off situations, like returning two values from a single function. But if you find yourself passing the same shape of data around in multiple functions, a struct is the better choice:

// With tuples — gets repetitive and hard to update:
func authenticate(_ user: (name: String, powerLevel: Int, guild: String)) { ... }
func showProfile(for user: (name: String, powerLevel: Int, guild: String)) { ... }
func signOut(_ user: (name: String, powerLevel: Int, guild: String)) { ... }

// With a struct — clean, reusable, and easy to update:
struct Hero {
    var name: String
    var powerLevel: Int
    var guild: String
}

func authenticate(_ hero: Hero) { ... }
func showProfile(for hero: Hero) { ... }
func signOut(_ hero: Hero) { ... }

If you ever need to add a new property — say, var rank: String — you only add it once to the struct, and every function automatically benefits. With tuples, you'd have to update every function signature manually.

Rule of thumb:

  • Use tuples for quick, one-off multi-value returns
  • Use structs when the same data shape appears in multiple places

Wrap Up

Term What It Means
Struct A custom data type with its own properties and methods
Property A variable or constant that belongs to a struct
Method A function that belongs to a struct
Instance A specific copy of a struct
Initializer The function used to create an instance
mutating Marks a method that changes a struct's properties

Structs are one of the most important building blocks in Swift — and in SwiftUI, almost everything you build will be a struct. Getting comfortable with them now will make everything that follows feel much more natural. 🌸


This article was written by me; AI was used to improve grammar and readability.