Delegate: ano ito, pattern ng delegasyon at mga protokol ng iOS

May-akda: IT Sectr Nai-publish: 2026-02-17 Oras ng pagbabasa: 9 min

Delegate — ay isang pattern ng disenyo kung saan ang isang bagay ay nagde-delegate ng pagpapatupad ng gawain sa ibang bagay. Sa iOS, ang pattern ay ipinapatupad sa pamamagitan ng Swift protokol at @protocol Objective-C. Ang Delegation ay isa sa mga pangunahing pattern ng Cocoa Touch, na ginagamit sa UITableViewDelegate, UITextFieldDelegate at daan-daang iba pang Apple API. Ayon sa Apple Developer Documentation (2025), humigit-kumulang 70% ng mga system class ng UIKit ay gumagamit ng mga delegat para sa pag-customize ng pag-uugali nang walang mana.

Mga Pangunahing Punto

  • Delegate — pattern kung saan ang bagay A ay nagde-delegate ng pagpapatupad ng gawain sa bagay B sa pamamagitan ng protokol o interface
  • Swift protokol ay tumutukoy sa isang hanay ng mga pamamaraan na maaari o dapat ipatupad ng delegat
  • Weak-referensiya sa delegat ay sapilitan upang maiwasan ang retain cycle at pagtagas ng memorya
  • UITableViewDelegate — ang pinakakaraniwang halimbawa ng delegat sa iOS na may 20+ opsyonal na pamamaraan
  • Pagkakaiba sa Observer: ang delegat ay relasyong 1:1, samantalang ang mga notipikasyon ay gumagana sa prinsipyong 1:N

Ano ang pattern ng Delegate?

Delegate — ay isang pattern ng disenyo ng pag-uugali na nagpapahintulot sa isang bagay na ilipat ang bahagi ng mga responsibilidad nito sa ibang bagay. Hindi tulad ng mana, kung saan ang klase ng anak ay nag-o-override ng mga pamamaraan ng magulang, ang delegat ay gumagamit ng komposisyon: ang bagay-may-ari ay nag-iimbak ng referensiya sa delegat at tumatawag ng mga pamamaraan nito sa mga tiyak na punto.

Ang delegat ay tumutukoy sa isang protokol — isang hanay ng mga pamamaraan na maaaring ipatupad ng delegat. Ang mga pamamaraan ay nahahati sa sapilitan (required) at opsyonal (optional). Sa Swift, ang mga opsyonal na pamamaraan ng protokol ay minamarkahan ng keyword na @objc optional.

Prinsipyo ng pagpapatakbo ng delegat

Ang bagay A (may-ari) ay naglalaman ng property na delegate — isang weak-referensiya sa bagay B (delegat). Kapag may nangyaring kaganapan, tinitingnan ni A kung ipinapatupad ni B ang kaukulang pamamaraan ng protokol at tinatawag ito. Weak-referensiya ay sapilitan: kung wala ito, hindi mapapalaya ang delegat mula sa memorya, dahil hawak siya ng may-ari ng matibay na referensiya.

Swift
protocol LoaderDelegate: AnyObject {
    func loaderDidStart(_ loader: DataLoader)
    func loader(_ loader: DataLoader, didLoad data: Data)
    func loader(_ loader: DataLoader, didFailWith error: Error)
}

class DataLoader {
    weak var delegate: LoaderDelegate?
    
    func start() {
        delegate?.loaderDidStart(self)
        // asynchronous na pag-load
    }
}

Ang klase na DataLoader ay tumutukoy sa protokol na LoaderDelegate at tumatawag ng mga pamamaraan ng delegat sa mga pangunahing punto ng siklo ng buhay ng pag-load. Ginagarantiya ng AnyObject na ang protokol ay maaari lamang ipatupad ng mga klase — ito ay kinakailangan para sa weak-referensiya.

Paano gumagana ang Delegate sa Swift?

Implementasyon ng delegat sa Swift ay may tatlong hakbang: pagdedeklara ng protokol, paggawa ng weak property na delegate sa may-ari, at pagpapatupad ng protokol sa klase-delegat. Tingnan natin ang halimbawa ng isang pasadyang UITextField na may validasyon.

Swift
protocol ValidatorDelegate: AnyObject {
    func validate(_ input: String) -> Bool
    func validatorDidFail(_ input: String)
}

class ValidatedTextField: UITextField {
    weak var validator: ValidatorDelegate?
    
    override func textDidChange() {
        guard let text = self.text else { return }
        if validator?.validate(text) == false {
            validator?.validatorDidFail(text)
            self.layer.borderColor = UIColor.red.cgColor
        }
    }
}

class LoginViewController: UIViewController, ValidatorDelegate {
    let textField = ValidatedTextField()
    
    override func viewDidLoad() {
        super.viewDidLoad()
        textField.validator = self
    }
    
    func validate(_ input: String) -> Bool {
        return input.count >= 6
    }
    
    func validatorDidFail(_ input: String) {
        print("Nabigo ang validasyon: masyadong maikli ang input")
    }
}

Ang LoginViewController ay nagpapatupad ng protokol na ValidatorDelegate at itinatakda ang sarili bilang delegat ng textField. Sa bawat pagbabago ng teksto, tinatawag ng ValidatedTextField ang validate(_:), at kung nabigo ang validasyon — validatorDidFail(_:). Ang Controller ay kumikilos bilang tagapamagitan sa pagitan ng View at ng lohika ng validasyon.

Delegate vs NotificationCenter vs Closure

Ang pagpili sa pagitan ng delegat, notipikasyon, at closure ay nakadepende sa bilang ng mga tatanggap at antas ng pagkakabit ng mga komponente. Bawat mekanismo ay lumulutas sa problema ng komunikasyon sa pagitan ng mga bagay, ngunit may iba't ibang trade-off.

KatangianDelegateNotificationCenterClosure
Uri ng koneksyon1:11:N1:1
PagkakabitMahina (sa pamamagitan ng protokol)Napakahina (string-susi)Katamtaman (pagkuha ng konteksto)
Kaligtasan ng uriBuoWala (Any?)Buo
Panganib ng retain cycleWala (weak)WalaOo (pagkuha ng self)
Kailan gagamitinMga komplikadong callback na may maraming pamamaraanMga kaganapang kinaiinteresan ng maramiMga simpleng closure na may 1-2 callback

Delegate ay optimal kapag kailangang magpadala ng serye ng mga kaugnay na kaganapan sa isang tatanggap. NotificationCenter ay mas mainam para sa broadcast na notipikasyon. Closure — para sa mga simpleng asinkronong operasyon, tulad ng completion handler sa URLSession.

Implementasyon ng Delegate sa Objective-C

Objective-C ay gumagamit ng @protocol at @optional para sa pagdedeklara ng mga delegat. Hindi tulad ng Swift, lahat ng pamamaraan ng protokol ay opsyonal bilang default. Ang pangunahing pagkakaiba — pagtawag sa respondsToSelector: bago magpadala ng mensahe sa delegat, dahil maaaring hindi naipatupad ang pamamaraan.

Objective-C
@protocol ImageCacheDelegate 
@optional
- (void)cacheDidStartDownload: (ImageCache *)cache;
- (void)cache: (ImageCache *)cache didCacheImage: (UIImage *)image;
@required
- (void)cache: (ImageCache *)cache didFailWithError: (NSError *)error;
@end

@interface ImageCache : NSObject
@property (nonatomic, weak) id<ImageCacheDelegate> delegate;
- (void)downloadImageAtURL: (NSURL *)url;
@end

@implementation ImageCache
- (void)downloadImageAtURL: (NSURL *)url {
    if ([self.delegate respondsToSelector:@selector(cacheDidStartDownload:)]) {
        [self.delegate cacheDidStartDownload:self];
    }
    // asynchronous na pag-load ng imahe
}
@end

Ang pangunahing pagkakaiba sa Objective-C: bago tumawag ng opsyonal na pamamaraan, kinakailangan ang pagsusuri ng respondsToSelector:. Sa Swift, ang mga opsyonal na pamamaraan ng protokol ay nag-aalis ng pagsusuring ito — ang optional chaining (?.) ay awtomatikong humahawak ng kaso ng kawalan ng implementasyon.

Karaniwang pagkakamali sa paggawa gamit ang mga delegat

Mga pagkakamali sa paggamit ng delegat ay humahantong sa pagtagas ng memorya, pag-crash ng app, at hindi halatang bug. Tingnan natin ang limang pinakakaraniwang problema.

Matibay na referensiya sa delegat

Retain cycle — ang pinakakaraniwang pagkakamali. Kung ang property na delegate ay idineklara bilang strong, at ang delegat naman ay nagmamay-ari ng bagay-may-ari, isang siklo ng pagpapanatili ang nabubuo. Ang parehong bagay ay hindi kailanman mapapalaya mula sa memorya. Solusyon: palaging ideklara ang delegat bilang weak var sa Swift o @property (weak) sa Objective-C.

Delegat hindi na-reset pagkatapos ng dealloc

Kung ang bagay-may-ari ay nabubuhay nang mas mahaba kaysa sa delegat at ang referensiya ay nananatili, ang pagtawag sa pamamaraan ng delegat ay hahantong sa EXC_BAD_ACCESS. Ang weak-referensiya ay awtomatikong lumulutas ng problemang ito: pagkatapos mapalaya ang delegat, ang property ay nagiging nil. Gayunpaman, sa mga multi-threaded na senaryo, mainam na suriin din ang delegat sa pangunahing thread.

Labis na bilang ng mga pamamaraan sa protokol

Ang protokol na may 20+ pamamaraan ay lumalabag sa prinsipyo ng paghihiwalay ng interface (ISP). Ang UITableViewDelegate ay naglalaman ng humigit-kumulang 30 opsyonal na pamamaraan — ito ay isang pangkasaysayang eksepsiyon. Sa sarili mong mga protokol, mas mainam na hatiin ang responsibilidad sa ilang maliliit na protokol, bawat isa ay may kanya-kanyang papel.

Mga halimbawa ng Delegate sa system API ng iOS

Ang system API ng Apple ay aktibong gumagamit ng pattern na Delegate. Tingnan natin ang tatlong pangunahing halimbawa mula sa UIKit na matatagpuan sa bawat iOS application.

APIProtokolMga pangunahing pamamaraan
UITableViewUITableViewDelegatedidSelectRowAt, heightForRowAt, willDisplay
UITextFieldUITextFieldDelegateshouldChangeCharactersIn, didBeginEditing, shouldReturn
URLSessionURLSessionDelegatedidReceiveChallenge, didCompleteWithError, didBecomeInvalidWithError

Bawat isa sa mga protokol na ito ay nagpapatupad ng iba't ibang aspeto ng pag-uugali: UITableViewDelegate ay namamahala ng hitsura at reaksyon sa pagpindot, UITextFieldDelegate ay kumokontrol ng input ng teksto, URLSessionDelegate ay nagpoproseso ng mga kaganapan sa network. Ipinapakita nito ang kakayahang umangkop ng pattern: ang delegat ay maaaring iakma sa anumang lugar ng responsibilidad.

Mga Madalas Itanong

Ano ang pagkakaiba ng delegate at dataSource sa iOS?

Delegate ay namamahala ng pag-uugali at hitsura (taas ng cell, reaksyon sa pagpindot). DataSource ay nagbibigay ng data (bilang ng mga row, nilalaman ng mga cell). Sa UITableViewDelegate at UITableViewDataSource — ito ay dalawang magkahiwalay na protokol na naghahati ng responsibilidad para sa presentasyon at data.

Bakit idineklara ang delegate bilang weak?

Weak-referensiya ay pumipigil sa retain cycle. Ang may-ari (hal. UITableView) ay hawak ang referensiya sa delegat bilang weak lamang. Kung ang delegat (UIViewController) ay nagmamay-ari ng table, ang matibay na referensiya sa delegat ay lilikha ng siklo: ViewController → UITableView → Delegate (ViewController). Weak ay pumuputol sa siklong ito.

Maaari bang gamitin ang delegate sa SwiftUI?

Sa SwiftUI, ang pattern na Delegate ay hindi gaanong ginagamit — ito ay pinapalitan ng @Binding, @State, at closure. Gayunpaman, ang delegate ay ginagamit pa rin para sa integrasyon ng UIKit sa pamamagitan ng UIViewRepresentable. Halimbawa, ang MKMapViewDelegate at WKUIDelegate ay nananatiling may kaugnayan kapag binabalot ang mga komponente ng UIKit sa SwiftUI.

Ano ang @objc optional sa mga protokol ng Swift?

@objc optional ay nagpapahintulot na magdeklara ng mga opsyonal na pamamaraan sa isang protokol ng Swift. Ito ay isang mekanismo ng kompatibilidad sa Objective-C runtime. Kung walang @objc, lahat ng pamamaraan ng protokol ng Swift ay sapilitan bilang default. Ang Optional ay ginagamit sa mga protokol ng UIKit, kung saan ang delegat ay maaari lamang magpatupad ng mga pamamaraan na kailangan niya.

Ilang delegat maaaring magkaroon ang isang bagay?

Ang isang bagay ay maaaring magkaroon ng isa lamang delegat para sa bawat property na delegate. Kung kailangan magpaalam sa maraming bagay, gamitin ang multicast delegate, isang array ng mga delegat, o NotificationCenter. Ang pattern na Delegate ay orihinal na dinisenyo bilang isang relasyong 1:1.

Buod

  • Delegate — pattern ng disenyo ng pag-uugali na naglilipat ng pagpapatupad ng gawain mula sa isang bagay patungo sa isa pa sa pamamagitan ng protokol
  • Swift protokol ay nagdedeklara ng isang hanay ng mga pamamaraan; ang mga opsyonal na pamamaraan ay minamarkahan ng @objc optional, ang mga sapilitan ay palaging ipinapatupad
  • Weak-referensiya sa delegat ay sapilitan upang maiwasan ang retain cycle at pagtagas ng memorya
  • UITableViewDelegate — ang pinakakilalang halimbawa; ang mga pamamaraan nito ay namamahala ng taas, pagpili, at pagpapakita ng mga cell
  • Delegate ay naiiba sa NotificationCenter sa relasyong 1:1 kumpara sa 1:N at buong kaligtasan ng uri
  • Objective-C ay nangangailangan ng pagsusuri ng respondsToSelector: para sa mga opsyonal na pamamaraan, Swift ay awtomatikong humahawak nito
  • Rekomendasyon: gamitin ang delegate para sa mga komplikadong callback na may maraming kaugnay na pamamaraan at closure para sa mga simpleng pagsasara

Gagawa kami ng mobile application na turnkey

Gumagawa ang IT Sectr ng mga iOS at Android application para sa mga startup at negosyo mula noong 2017. Magpapayo kami sa iyo at magmumungkahi ng pinakamahusay na solusyon.

Pag-usapan ang proyekto

Basahin din