@import - #import - iOS 7


432

Bazı yeni iOS 7 özellikleriyle oynuyorum ve WWDC videosu "iOS'ta İlgi Çekici Kullanıcı Arayüzünü Uygulama" bölümünde tartışıldığı gibi bazı Görüntü Efektleri ile çalışıyorum. Oturumun kaynak kodunda bir bulanıklık efekti üretmek için, UIImageUIKit'i şu şekilde ithal eden bir kategori aracılığıyla genişletildi:

@import UIKit;

Sanırım başka bir oturum videosunda bununla ilgili bir şey gördüm ama bulmakta zorlanıyorum. Bunu ne zaman kullanacağım hakkında arka plan bilgisi arıyorum. Yalnızca Apple çerçeveleriyle kullanılabilir mi? Bu derleyici yönergesini kullanmanın faydaları geri dönüp eski kodu güncellemem için yeterli mi?


Yanıtlar:


838

Modüller veya "anlamsal içe aktarma" adı verilen yeni bir özelliktir . Oturum 205 ve 404 için WWDC 2013 videolarında daha fazla bilgi var . Önceden derlenmiş başlıkların daha iyi uygulanmasıdır. İOS 7 ve Mavericks'teki sistem çerçevelerinden herhangi biriyle modülleri kullanabilirsiniz. Modüller, yürütülebilir çerçeve ve üstbilgileri ile birlikte bir pakettir ve daha güvenli ve daha verimli olarak lanse edilir .#import

Kullanmanın büyük avantajlarından biri @importolduğunu otomatik olarak yapılır, proje ayarlarında çerçeveyi eklemek gerekmez . Bu, artı düğmesini tıkladığınız adımı atlayıp çerçeveyi (altın araç kutusu) arayabilir ve ardından "Çerçeveler" grubuna taşıyabileceğiniz anlamına gelir. Birçok geliştiriciyi şifreli "Linker hatası" mesajlarından kurtaracaktır.

@importAnahtar kelimeyi kullanmanıza gerek yoktur . Modülleri kullanmayı seçerseniz, tüm #importve #includeyönergeler @importotomatik olarak kullanılacak şekilde eşlenir . Bu, kaynak kodunuzu (veya başka bir yerden indirdiğiniz kitaplıkların kaynak kodunu) değiştirmeniz gerekmediği anlamına gelir. Sözde modüllerin kullanılması, özellikle PCH'leri iyi kullanmadıysanız veya projenizde çok sayıda küçük kaynak dosyası varsa, yapı performansını da artırır.

Modüller çoğu Apple çerçevesi için önceden oluşturulmuştur (UIKit, MapKit, GameKit, vb.). Bunları kendiniz oluşturduğunuz çerçevelerle kullanabilirsiniz: Xcode'da bir Swift çerçevesi oluşturursanız otomatik olarak oluşturulur ve herhangi bir Apple veya 3. taraf kitaplığı için kendiniz el ile bir ".modulemap" dosyası oluşturabilirsiniz .

Kullanılabilir çerçevelerin listesini görmek için kod tamamlamayı kullanabilirsiniz:

resim açıklamasını buraya girin

Xcode 5'te yeni projelerde modüller varsayılan olarak etkindir . Daha eski bir projede etkinleştirmek için proje oluşturma ayarlarınıza gidin, "Modüller" için arama yapın ve "Modülleri Etkinleştir" i "EVET" olarak ayarlayın. "Bağlantı Çerçeveleri" de "EVET" olmalıdır:

Xcode 5 ve iOS 7 veya Mavericks SDK kullanıyor olmalısınız, ancak eski işletim sistemleri için de yayınlayabilirsiniz (örneğin iOS 4.3 veya başka bir şey). Modüller, kodunuzun oluşturulma şeklini veya kaynak kodlardan herhangi birini değiştirmez.


WWDC slaytlarından:

  • Bir çerçevenin tam anlamsal açıklamasını içe aktarır
  • Üstbilgileri ayrıştırmaya gerek yoktur
  • Bir çerçevenin arayüzünü içe aktarmanın daha iyi yolu
  • İkili gösterim yükler
  • Önceden derlenmiş başlıklardan daha esnek
  • Yerel makro tanımlarının etkilerine karşı bağışıklık (örn. #define readonly 0x01)
  • Yeni projeler için varsayılan olarak etkindir

Modülleri açıkça kullanmak için:

Değiştir #import <Cocoa/Cocoa.h>ile@import Cocoa;

Bu gösterimle yalnızca bir başlık da içe aktarabilirsiniz:

@import iAd.ADBannerView;

Alt modüller Xcode'da sizin için otomatik tamamlanır.


15
@DaveDeLong & Klaas: Teşekkürler! Bunu ilk cevapladığımda modüller hakkında hiçbir şey bilmediğimi itiraf etmeliyim. Gidip 404. Oturumu izlemek için izledim. Doug Gregor'un (LLVM adamı) verdiği sunum gerçekten çok iyi oldu. Ayrıca burada avantajları açıklayan bir C ++ Modülleri konuşması var: youtube.com/watch?v=4Xo9iH5VLQ0
nevan king

3
@ nevan-- cevap için teşekkürler. Sadece modüllerin şu anda 3. tarafı ve kendi çerçevelerinizi desteklemediğini eklemek istedim.
jamdaddy25

Bunu kendi sınıflarınız için kullanabilir misiniz?
cfischer

5
Uygun bir module.map sağlanırsa 3. taraf çerçevelerini içe aktarmanız gerektiğini düşünüyorum. LLVM clang modülü belgeleri: clang.llvm.org/docs/Modules.html#module-map-language
bames53

1
Oh, aslında @import sqlite3benim için çalıştı gibi görünüyor çünkü bunun için kendi module.map'i oluşturdum ve sqlite'ın OS X'e eklendiğini ve module.map'i çıkardığımda, derleyici eski modülü kullanmaya devam etti.
bames53

46

Objective-C ile Kakao Öğrenme kitabında bulabileceğiniz hoş bir cevap (ISBN: 978-1-491-90139-7)

Modüller, dosyaları ve kütüphaneleri projelerinize dahil etmenin ve bağlantılandırmanın yeni bir yoludur. Modüllerin nasıl çalıştığını ve ne gibi avantajlara sahip olduklarını anlamak için, Objective-C ve #import deyiminin geçmişine geri bakmak önemlidir.

#import "someFile.h"

Veya çerçeveler söz konusu olduğunda:

#import <SomeLibrary/SomeFile.h>

Objective-C, C programlama dilinin bir üst kümesi olduğundan, #import durumu C'nin #includeifadesine göre küçük bir ayrıntılandırmadır . #İnclude deyimi çok basittir; derleme sırasında dahil edilen dosyada bulduğu her şeyi kodunuza kopyalar. Bu bazen önemli sorunlara neden olabilir. Örneğin, iki başlık dosyanız olduğunu düşünün: SomeFileA.hve SomeFileB.h; SomeFileA.hiçerir SomeFileB.hve SomeFileB.hiçerir SomeFileA.h. Bu bir döngü oluşturur ve coimpiler'ı karıştırabilir. Bununla başa çıkmak için, C programcıları bu tür olaylara karşı korumalar yazmalıdır.

Kullanırken #import, bu sorun hakkında endişelenmenize veya önlemek için başlık korumaları yazmanıza gerek yoktur. Bununla birlikte, #importhala sadece yüceltilmiş bir kopyala-yapıştır eylemi, diğer daha küçük ama yine de çok tehlikeli konular arasında yavaş derleme süresine neden oluyor (kendi kodunuzda başka bir yerde bildirdiğiniz bir şeyi geçersiz kılan bir dosya gibi).

Modüller bunun üstesinden gelmek için bir girişimdir. Artık kaynak koduna bir kopyala ve yapıştır değil, yalnızca gerektiğinde ve yerde kaynak kodunuza alınabilen içerilen dosyaların serileştirilmiş bir temsilidir. Modülleri kullanarak, kod genellikle daha hızlı derlenir ve #include veya #import.

Bir çerçeveyi içe aktarmak için önceki örneğe dönme:

#import <SomeLibrary/SomeFile.h>

Bu kütüphaneyi modül olarak içe aktarmak için kod şu şekilde değiştirilecektir:

@import SomeLibrary;

Bu, SomeLibrary çerçevesini otomatik olarak projeye bağlayan Xcode ek bonusuna sahiptir. Modüller ayrıca yalnızca gerçekten ihtiyaç duyduğunuz bileşenleri projenize dahil etmenizi sağlar. Örneğin, AwesomeObject bileşenini AwesomeLibrary çerçevesinde kullanmak istiyorsanız, normalde her şeyi sadece tek parçayı kullanmak için içe aktarmanız gerekir. Ancak, modülleri kullanarak kullanmak istediğiniz belirli nesneyi içe aktarabilirsiniz:

@import AwesomeLibrary.AwesomeObject;

Xcode 5'te yapılan tüm yeni projeler için modüller varsayılan olarak etkindir. Modülleri eski projelerde kullanmak istiyorsanız (ve gerçekten yapmanız gerekir) projenin derleme ayarlarında etkinleştirilmeleri gerekir. Bunu yaptıktan sonra, herhangi bir endişe duymadan kodunuzdaki hem #importve @importifadeleri birlikte kullanabilirsiniz .


Projemde (Xcode 6) modülleri etkinleştirmek için Xcode 4'te ilk başlattığım bir seçenek yok. Bir şekilde manuel olarak ekleyebilir miyim?
Awesome-o

Hedef oluşturma iOS 6, bence sorun bu
Awesome-o

4

Şu anda yalnızca yerleşik sistem çerçeveleri için çalışıyor. #importApple gibi kullanıyorsanız , yine UIKitde uygulama temsilcisindeki çerçeveyi içe aktarırsanız (değiştirilirse (modüller açıksa ve bir sistem çerçevesi olarak tanınırsa) ve derleyici, üstbilgi dosyalarının içe aktarılması değil, bir modül içe aktarımı olarak yeniden eşleştirecektir. . Bu nedenle, bırakma, #importmümkün olduğunda bir modül ithalatına dönüştürülmesiyle aynı olacaktır.



1

Modül kullanmanın birkaç faydası vardır. Modül haritası oluşturulmadıkça yalnızca Apple'ın çerçevesiyle kullanabilirsiniz. dosyaya @importeklendiğinde derleme üstbilgi dosyalarına biraz benzer, .pchbu da derleme işlemini ayarlamanın bir yoludur. Ek olarak, eski yollardan kitaplık eklemeniz gerekmez @import, aslında çok daha hızlı ve etkilidir. Hala güzel bir referans arıyorsanız, bu makaleyi okumanızı şiddetle tavsiye ederim .


0

Tarih:

#include => #import => .pch => @import

#include vs #import
.pch - Önceden derlenmiş başlık

Modül - @import

Product Name == Product Module Name 

@moduleDeklarasyon derleyiciye, inşa süresini kısaltan , önceden derlenmiş bir çerçeve ikili dosyası yüklemeyi söylüyor . Modüler Çerçeve [Hakkında] içerir.modulemap

Xcode projesinde modül özelliği etkinleştirilirse #includeve #importdirektifler otomatik olarak dönüştürülürse @import, tüm avantajları getirir.

resim açıklamasını buraya girin

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.