दस्तावेज़ में केवल नेस्टेड प्रकारों का उल्लेख है, लेकिन यह स्पष्ट नहीं है कि क्या उन्हें नामस्थान के रूप में उपयोग किया जा सकता है। मुझे नामस्थानों का कोई स्पष्ट उल्लेख नहीं मिला है।
दस्तावेज़ में केवल नेस्टेड प्रकारों का उल्लेख है, लेकिन यह स्पष्ट नहीं है कि क्या उन्हें नामस्थान के रूप में उपयोग किया जा सकता है। मुझे नामस्थानों का कोई स्पष्ट उल्लेख नहीं मिला है।
जवाबों:
Apple देव फोरम में सेवनटेलेवेन द्वारा उत्तर दिया गया :
नाम-स्थान प्रति-फ़ाइल नहीं हैं; वे प्रति-लक्ष्य ("उत्पाद मॉड्यूल नाम" बिल्ड सेटिंग के आधार पर) हैं। तो आप कुछ इस तरह से समाप्त करेंगे:
import FrameworkA import FrameworkB FrameworkA.foo()
सभी स्विफ्ट घोषणाओं को कुछ मॉड्यूल का हिस्सा माना जाता है, इसलिए जब आप कहते हैं कि "
NSLog
" (हाँ, यह अभी भी मौजूद है) तो आपको स्विफ्ट के बारे में "Foundation.NSLog
" जैसा लगता है ।
साथ ही क्रिस लैटनर ने नेमस्पेसिंग के बारे में ट्वीट किया ।
Namespacing स्विफ्ट में निहित है, सभी वर्गों (आदि) वे मॉड्यूल (Xcode लक्ष्य) द्वारा स्पष्ट रूप से scoped हैं वे में हैं। कोई वर्ग उपसर्ग की जरूरत नहीं है।
बहुत अलग लगता है कि मैं क्या सोच रहा था।
forums.developer.apple.com
दुर्भाग्य से, नए मंचों में उस धागे को आयात नहीं किया है ।
मैं स्विफ्ट के नामकरण को आकांक्षा के रूप में वर्णित करूंगा; इसे बहुत सारे विज्ञापन दिए गए हैं जो जमीन पर किसी भी सार्थक वास्तविकता के अनुरूप नहीं हैं।
उदाहरण के लिए, WWDC वीडियो बताता है कि यदि आप जो फ्रेमवर्क आयात कर रहे हैं, उसमें एक वर्ग MyClass है और आपके कोड में एक वर्ग MyClass है, तो वे नाम संघर्ष नहीं करते हैं क्योंकि "name mangling" उन्हें अलग आंतरिक नाम देता है। वास्तव में, हालांकि, वे संघर्ष करते हैं, इस अर्थ में कि आपका अपना कोड MyClass जीतता है, और आप निर्दिष्ट नहीं कर सकते "नहीं नहीं, मेरा मतलब फ्रेमवर्क में MyClass" है - यह कहना TheFramework.MyClass
काम नहीं करता है (संकलक जानता है कि आपका क्या मतलब है , लेकिन यह कहता है कि यह फ्रेमवर्क में ऐसा वर्ग नहीं खोज सकता है)।
मेरा अनुभव यह है कि स्विफ्ट मामूली नाम नहीं है। ऑब्जेक्टिव-सी से स्विफ्ट में मेरे एक ऐप को चालू करने में, मैंने एक एम्बेडेड फ्रेमवर्क बनाया क्योंकि यह करना इतना आसान और अच्छा था। हालाँकि, फ्रेमवर्क को आयात करना, फ्रेमवर्क के सभी स्विफ्ट सामानों को आयात करता है - इसलिए प्रेस्टो, एक बार फिर सिर्फ एक नाम स्थान है और यह वैश्विक है। और कोई स्विफ्ट हेडर नहीं हैं इसलिए आप किसी भी नाम को छिपा नहीं सकते हैं।
EDIT: बीज 3 में, यह सुविधा अब ऑनलाइन होने लगी है, निम्नलिखित अर्थों में: यदि आपके मुख्य कोड में MyClass है और आपके ढांचे में MyFramework में MyClass शामिल है, तो पूर्ववर्ती डिफ़ॉल्ट रूप से उत्तरार्द्ध को पूरा करता है, लेकिन आप फ्रेमवर्क में एक तक पहुँच सकते हैं। सिंटैक्स का उपयोग करके MyFramework.MyClass
। इस प्रकार हम वास्तव में एक अलग नामस्थान की अशिष्टता है!
संपादित 2: बीज 4 में, अब हमारे पास पहुंच नियंत्रण है! इसके अलावा, मेरे एक ऐप में मेरे पास एक एम्बेडेड फ्रेमवर्क और पर्याप्त रूप से पर्याप्त है, सब कुछ डिफ़ॉल्ट रूप से छिपा हुआ था और मुझे सार्वजनिक एपीआई के सभी बिट्स को स्पष्ट रूप से उजागर करना था। यह एक बड़ा सुधार है।
Foundation.NSArray
।
इसके साथ कुछ प्रयोग करते हुए मैंने रूट "पैकेज" का विस्तार करके अपनी फाइलों में इन "नामांकित" कक्षाओं का निर्माण किया। यकीन नहीं होता कि क्या यह सर्वोत्तम प्रथाओं के खिलाफ है या यदि इसका कोई निहितार्थ है तो मैं इसके बारे में (?)
AppDelegate.swift
var n1 = PackageOne.Class(name: "Package 1 class")
var n2 = PackageTwo.Class(name: "Package 2 class")
println("Name 1: \(n1.name)")
println("Name 2: \(n2.name)")
PackageOne.swift
import Foundation
struct PackageOne {
}
PackageTwo.swift
import Foundation
struct PackageTwo {
}
PackageOneClass.swift
extension PackageOne {
class Class {
var name: String
init(name:String) {
self.name = name
}
}
}
PackageTwoClass.swift
extension PackageTwo {
class Class {
var name: String
init(name:String) {
self.name = name
}
}
}
संपादित करें:
बस पता चला है कि अलग-अलग फ़ाइलों का उपयोग करते हुए उपरोक्त कोड में "सबपैकेज" बनाने का काम नहीं होगा। शायद कोई संकेत दे सकता है कि ऐसा क्यों होगा?
उपरोक्त फ़ाइलों को जोड़ना:
PackageOneSubPackage.swift
import Foundation
extension PackageOne {
struct SubPackage {
}
}
PackageOneSubPackageClass.swift
extension PackageOne.SubPackage {
class Class {
var name: String
init(name:String) {
self.name = name
}
}
}
संकलक त्रुटि को फेंकना: 'सबपैकेज' 'पैकेजऑन' का सदस्य प्रकार नहीं है
अगर मैं PackageOneSubPackageClass.swift से PackageOneSubPackage.swift कोड काम करता हूं तो कोड को स्थानांतरित करता हूं। किसी को?
2 संपादित करें:
इस के साथ अभी भी चारों ओर फिडिंग और पता चला (Xcode 6.1 बीटा 2 में) कि एक फ़ाइल में संकुल को परिभाषित करके उन्हें अलग-अलग फ़ाइलों में बढ़ाया जा सकता है:
public struct Package {
public struct SubPackage {
public struct SubPackageOne {
}
public struct SubPackageTwo {
}
}
}
यहाँ एक फाइल में मेरी फाइलें हैं: https://gist.github.com/mikajauhonen/d4b3e517122ad6a132b8
मेरा मानना है कि यह प्रयोग करके हासिल किया गया है:
struct Foo
{
class Bar
{
}
}
तब इसका उपयोग करके पहुँचा जा सकता है:
var dds = Foo.Bar();
enum
ए का उपयोग करते हैं , ए का नहीं struct
, इसलिए आप तत्काल नहीं कर सकते Foo
।
स्विफ्ट अजगर की तरह मॉड्यूल का उपयोग करता है ( यहाँ और यहाँ देखें ) और जैसा कि @ केविन सिल्वेस्ट्रे ने सुझाव दिया है कि आप नेस्टेड प्रकारों को नेमस्पेस के रूप में भी उपयोग कर सकते हैं ।
और डब्ल्यूडीडीसी में @ डैनियल ए व्हाइट से जवाब का विस्तार करने के लिए वे स्विफ्ट में मॉड्यूल के बारे में बात कर रहे थे।
इसके अलावा यहां समझाया गया है:
इंफ़र्ड किए गए प्रकार कोड क्लीनर और गलतियों की कम संभावना रखते हैं, जबकि मॉड्यूल हेडर को खत्म करते हैं और नाम स्थान प्रदान करते हैं।
जब आप मौजूदा ढांचे में कक्षा के समान नाम के साथ वर्ग को परिभाषित करने की आवश्यकता हो तो नाम स्थान उपयोगी होते हैं ।
मान लीजिए कि आपके ऐप का
MyApp
नाम है, और आपको अपना रिवाज घोषित करने की आवश्यकता हैUICollectionViewController
।
आपको इस तरह उपसर्ग और उपवर्ग की आवश्यकता नहीं है :
class MAUICollectionViewController: UICollectionViewController {}
इसको ऐसे करो:
class UICollectionViewController {} //no error "invalid redeclaration o..."
क्यों? । क्योंकि आपने जो घोषित किया है वह वर्तमान मॉड्यूल में घोषित किया गया है , जो कि आपका वर्तमान लक्ष्य है । और UICollectionViewController
से UIKit
में घोषित किया जाता है UIKit
मॉड्यूल।
वर्तमान मॉड्यूल के भीतर इसका उपयोग कैसे करें?
var customController = UICollectionViewController() //your custom class
var uikitController = UIKit.UICollectionViewController() //class from UIKit
उन्हें दूसरे मॉड्यूल से कैसे अलग किया जाए?
var customController = MyApp.UICollectionViewController() //your custom class
var uikitController = UIKit.UICollectionViewController() //class from UIKit
आप सही के प्रति अपने सभी कोड को इंडेंट करने के बिना नेमस्पेसिंग के लिए extension
उल्लेखित struct
दृष्टिकोण का उपयोग करने के लिए उपयोग कर सकते हैं । मैं इसके साथ थोड़ा सा जुड़ गया हूं और मुझे यकीन नहीं है कि मैं बनाने Controllers
और Views
नीचे दिए गए उदाहरणों की तरह नामस्थान पर जाऊंगा , लेकिन यह बताता है कि यह कितनी दूर जा सकता है:
Profiles.swift :
// Define the namespaces
struct Profiles {
struct Views {}
struct ViewControllers {}
}
प्रोफ़ाइल / ViewControllers / Edit.swift
// Define your new class within its namespace
extension Profiles.ViewControllers {
class Edit: UIViewController {}
}
// Extend your new class to avoid the extra whitespace on the left
extension Profiles.ViewControllers.Edit {
override func viewDidLoad() {
// Do some stuff
}
}
प्रोफ़ाइल / दृश्य / Edit.swift
extension Profiles.Views {
class Edit: UIView {}
}
extension Profiles.Views.Edit {
override func drawRect(rect: CGRect) {
// Do some stuff
}
}
मैंने इसे एक ऐप में उपयोग नहीं किया है क्योंकि मुझे इस अलगाव के स्तर की अभी तक ज़रूरत नहीं है लेकिन मुझे लगता है कि यह एक दिलचस्प विचार है। यह सर्वव्यापी * ViewController प्रत्यय जैसे वर्ग प्रत्यय की आवश्यकता को भी दूर करता है जो गुस्सा लंबे समय तक है।
हालाँकि, यह किसी भी चीज को छोटा नहीं करता है जब इसे संदर्भित किया जाता है जैसे कि इस तरह की विधि मापदंडों में:
class MyClass {
func doSomethingWith(viewController: Profiles.ViewControllers.Edit) {
// secret sauce
}
}
यदि कोई व्यक्ति उत्सुक था, तो 10 जून 2014 तक, यह स्विफ्ट में एक ज्ञात बग है:
से SevenTenEleven
"ज्ञात बग, क्षमा करें! Rdar: // समस्या / 17127940 क्वालिफाइंग स्विफ्ट प्रकार उनके मॉड्यूल नाम से काम नहीं करता है।"