在Objective-C实例中,数据可以是公共的、受保护的或私有的。例如:

@interface Foo : NSObject
{
  @public
    int x;
  @protected:
    int y;
  @private:
    int z;
  }
-(int) apple;
-(int) pear;
-(int) banana;
@end

我没有发现任何提到的访问修饰符在Swift参考。是否有可能限制Swift中数据的可见性?


当前回答

你可以使用的一个选项是将实例创建包装到一个函数中,并在构造函数中提供适当的getter和setter:

class Counter {
    let inc: () -> Int
    let dec: () -> Int

    init(start: Int) {
        var n = start

        inc = { ++n }
        dec = { --n }
    }
}


let c = Counter(start: 10)

c.inc()  // 11
c.inc()  // 12
c.dec()  // 11

其他回答

从Xcode 6 beta 4开始,Swift就有了访问修饰符。发布说明如下:

Swift访问控制分为三种访问级别: 私有实体只能从定义它们的源文件中访问。 内部实体可以在目标中定义它们的任何地方访问。 公共实体可以从目标中的任何地方访问,也可以从导入当前目标模块的任何其他上下文访问。

隐式默认值是内部的,因此在应用程序目标中,您可以关闭访问修饰符,除非在需要更严格限制的地方。在框架目标中(例如,如果你嵌入一个框架来在应用程序和共享或Today视图扩展之间共享代码),使用public指定你想要向框架的客户端公开的API。

你可以使用的一个选项是将实例创建包装到一个函数中,并在构造函数中提供适当的getter和setter:

class Counter {
    let inc: () -> Int
    let dec: () -> Int

    init(start: Int) {
        var n = start

        inc = { ++n }
        dec = { --n }
    }
}


let c = Counter(start: 10)

c.inc()  // 11
c.inc()  // 12
c.dec()  // 11

在Beta 6中,文档指出有三种不同的访问修饰符:

公共 内部 私人

这三点适用于类、协议、函数和属性。

public var somePublicVariable = 0
internal let someInternalConstant = 0
private func somePrivateFunction() {}

有关更多信息,请检查访问控制。

现在在测试版4中,他们为Swift添加了访问修饰符。

from Xcode 6 beta 4 realese notes:

Swift access control has three access levels: private entities can only be accessed from within the source file where they are defined. internal entities can be accessed anywhere within the target where they are defined. public entities can be accessed from anywhere within the target and from any other context that imports the current target’s module. By default, most entities in a source file have internal access. This allows application developers to largely ignore access control while allowing framework developers full control over a framework's API.

从Swift 3.0.1开始,共有4个访问级别,从最高(限制最少)到最低(限制最多)。


1. 公开和公共

允许在定义模块(目标)之外使用一个实体。在指定框架的公共接口时,通常使用开放或公共访问。

然而,开放访问仅适用于类和类成员,它与公共访问的区别如下:

公共类和类成员只能在定义模块(目标)内进行子类化和重写。 开放类和类成员可以在定义模块(目标)内外被子类化和重写。

// First.framework – A.swift

open class A {}

// First.framework – B.swift

public class B: A {} // ok

// Second.framework – C.swift

import First

internal class C: A {} // ok

// Second.framework – D.swift

import First

internal class D: B {} // error: B cannot be subclassed

2. 内部

启用在定义模块(目标)中使用的实体。在定义应用程序或框架的内部结构时,通常使用内部访问。

// First.framework – A.swift

internal struct A {}

// First.framework – B.swift

A() // ok

// Second.framework – C.swift

import First

A() // error: A is unavailable

3.fileprivate

将实体的使用限制到其定义的源文件。当在整个文件中使用特定功能块的实现细节时,通常使用文件私有访问来隐藏这些细节。

// First.framework – A.swift

internal struct A {

    fileprivate static let x: Int

}

A.x // ok

// First.framework – B.swift

A.x // error: x is not available

4. 私人

将实体的使用限制在其封闭声明范围内。当只在单个声明中使用特定功能块的实现细节时,通常使用私有访问来隐藏这些细节。

// First.framework – A.swift

internal struct A {

    private static let x: Int

    internal static func doSomethingWithX() {
        x // ok
    }

}

A.x // error: x is unavailable