Что является хорошим примером для различения fileprivate и private в Swift3

Эта статья была полезной для понимания новых спецификаций доступа в Swift 3 . В нем также приводятся некоторые примеры использования fileprivate и private .

Мой вопрос: не использует fileprivate для функции, которая будет использоваться только в этом файле так же, как с помощью private ?

fileprivate теперь то, что private раньше было в предыдущих версиях Swift: доступно из одного и того же исходного файла. Объявление, помеченное как private теперь доступно только в пределах лексической области, в которой оно объявлено. Таким образом, private является более ограничивающим, чем fileprivate .

С Swift 4 частные объявления внутри типа доступны для расширений того же типа, если расширение определено в том же исходном файле.

Пример (все в одном исходном файле):

 class A { private func foo() {} fileprivate func bar() {} func baz() { foo() bar() } } extension A { func test() { foo() // Swift 3: error: use of unresolved identifier 'foo' // Swift 4: no error because extension is in same source file bar() } } let a = A() a.foo() // error: 'foo' is inaccessible due to 'private' protection level a.bar() 
  • Частный метод foo доступен только в рамках определения class A { ... } . Он даже не доступен из расширения к типу (в Swift 3, см. Второе примечание ниже для изменений в Swift 4).

  • Метод file-private bar доступен из того же исходного файла.

Заметки:

  1. Предложение SE-0159 – Fix Частных Уровней доступа предложил вернуться к Swift 2 семантике Swift 4. После длительной и противоречивой дискуссии о быстротекущей эволюции списка рассылки, это предложение было отвергнуто .

  2. Предложение SE-0169 – Улучшение взаимодействия между частными декларациями и расширениями предлагает сделать private объявления внутри типа, доступного для расширений того же типа, если расширение определено в том же исходном файле. Это предложение было принято и реализовано в Swift 4.

Я просто рисую диаграмму о private , fileprivate , open и public

Надеюсь, он может быстро помочь вам, для описания текста, пожалуйста, обратитесь к ответу Мартина R

[Обновить Swift 4]

введите описание изображения здесь

Практическое эмпирическое правило состоит в том, что вы используете private для переменных, констант, внутренних структур и classов, которые используются только внутри объявления вашего classа / структуры. Вы используете fileprivate для вещей, которые используются внутри ваших расширений в том же файле, что и ваш class / структура, но за пределами их определяющих фигурных скобок (то есть их лексической области).

  class ViewController: UIViewController { @IBOutlet var tableView: UITableView! //This is not used outside of class Viewcontroller private var titleText = "Demo" //This gets used in the extension fileprivate var list = [String]() override func viewDidLoad() { navigationItem.title = titleText } } extension ViewController: UITableViewDataSource { func numberOfSections(in tableView: UITableView) -> Int { return list.count } } 

Хотя ответы @ MartinR и @ StephenChen идеальны, Swift 4 немного меняет ситуацию.

Частный в настоящее время считается закрытым для classа, в котором он объявлен, а также его расширений.

FilePrivate считается приватным в этом файле, если это class, в котором определена переменная, ее расширение или любые другие classы, определенные в этом же файле.

В следующем примере языковые конструкции, измененные private и fileprivate видимому, ведут себя одинаково:

 fileprivate func fact(_ n: Int) -> Int { if (n == 0) { return 1 } else { return n * fact(n - 1) } } private func gauss(_ n: Int) -> Int { if (n == 0) { return 0 } else { return n + gauss(n - 1) } } print(fact(0)) print(fact(5)) print(fact(3)) print(gauss(10)) print(gauss(9)) 

Полагаю, это по интуиции. Но есть ли какие-то исключения?

С наилучшими пожеланиями.

В Swift 4.0 Private теперь доступен в расширении, но в том же файле. Если вы объявляете / определяете расширение в другом файле, ваша личная переменная не будет доступна для вашего расширения **

Файл приватный
Файло-частный доступ ограничивает использование объекта в собственном определяющем исходном файле. Используйте файл-частный доступ, чтобы скрыть детали реализации определенной функциональности, когда эти данные используются во всем файле.
Синтаксис: fileprivate
Пример: fileprivate class SomeFilePrivateClass {}

Частный
Частный доступ ограничивает использование объекта в объявлении, заключенном в оболочку, и к расширениям этого объявления, которые находятся в одном файле . Используйте частный доступ, чтобы скрыть детали реализации определенной функциональности, когда эти данные используются только в рамках одной декларации.
Синтаксис: private
Пример: private class SomePrivateClass {}

Ниже приведено более подробное описание всех уровней доступа: Swift – Уровни доступа

Посмотрите на это изображение:
Файл: ViewController.swift
Здесь controller расширения и представления находится в одном файле, поэтому частная переменная testPrivateAccessLevel доступна в расширении

введите описание изображения здесь

Файл: TestFile.swift
Здесь controller расширения и представления находится в разных файлах, поэтому закрытая переменная testPrivateAccessLevel недоступна в расширении.

введите описание изображения здесь

введите описание изображения здесь

Здесь class ViewController2 является подclassом ViewController и оба находятся в одном файле. Здесь частная переменная testPrivateAccessLevel недоступна в подclassе, но fileprivate доступен в подclassе.

введите описание изображения здесь

 class Privacy { fileprivate(set) var pu:Int { get { return self.pr } set { self.pr = newValue } } private var pr:Int = 0 fileprivate var fp:Int = 0 func ex() { print("\(self.pu) == \(self.pr) and not \(self.fp)") } } extension Privacy { func ex2() { self.pu = 5 self.ex() } } 

Мне это нравится, потому что это очень просто для иваров.

Попробуйте изменить fileprivate на частный (и наоборот) и посмотреть, что происходит при компиляции …

filePrivate – уровень контроля доступа находится внутри файла.

case 1 : Если мы создаем расширение в том же файле classа и попытаемся получить доступ к функции fileprivate или fileprivate в своем расширении – разрешен доступ
case 2 : если мы создадим расширение classа в новом файле – и теперь попробуйте получить доступ к функции fileprivate или fileprivate – доступ не разрешен

уровень доступа к частному доступу находится в лексической области

case 1 : Если свойство или функция объявлено как private в classе, то по умолчанию class по умолчанию является classом. case 2 : если частный экземпляр объявлен с телом функции, то область экземпляра ограничена телом функции.

  • Shuffle array swift 3
  • Держите окно всегда сверху?
  • Добавить локальное уведомление в ios10 - быстрый 3
  • Alamofire Swift 3.0 Дополнительный аргумент в вызове
  • попробуйте, попробуйте! & пытаться? какая разница, и когда использовать их?
  • Доступ к коду в Swift 3 Error
  • «Classname не имеет имени участника» при добавлении цели UIButton
  • Как я могу конкатенировать несколько необязательных строк в swift 3.0?
  • Swift 3 для цикла с приращением
  • Правильно Разбор JSON в Swift 3
  • Как остановить DispatchWorkItem в GCD?
  • Давайте будем гением компьютера.