Objective c: делегирование метода неявно вызывает другой экземпляр

#ios #objective-c

#iOS #objective-c

Вопрос:

У меня есть класс, который принимает делегат и, конечно, вызывает методы делегата в какой-то момент времени, в этом примере NSURLConnection :

 NSURLConnection *theConnection = [[NSURLConnection alloc]
                                   initWithRequest:request
                                   delegate:delegate];
  

Я хочу перехватить didFailWithError метод делегата, т. Е. Экземпляр NSURLConnection не вызывает метод делегата напрямую, вместо этого он вызывает другой метод, который вызывает в didFailWithError конечном итоге.

То, что я хотел бы сделать, это что-то вроде «наследования» на объекте вместо уровня класса. Например, в javascript я бы сделал что-то вроде:

 // Set the original delegate as prototype
var myDecoratedDelegate = Object.create(delegate);
// save the original method
var didFailWithError = delegate.didFailWithError;
// Decorate the didFailWithError method
myDecoratedDelegate.didFailWithError = function() {
    // do something
    didFailWithError()
}
var connection = new Connection(request, myDecoratedDelegate);
  

Таким образом, я бы заархивировал, чтобы каждый метод исходного делегата вызывался нормально, за исключением функции, которую я хотел бы украсить.

Я знаю, objective c — это не javascript, но я довольно новичок в objective c, и, возможно, есть элегантное решение.

Однако я знаю, что с method_setImplementation помощью вас можно изменить реализацию методов экземпляров. Однако я думаю, что для вызываемого абонента было бы довольно неожиданно, если бы я изменил исходное поведение класса и предпочел бы этого не делать.

Приемлемым решением для меня также было бы наследовать NSURLConnection класс и изменить способ, которым он вызывает своего делегата. Однако я не знаю, как это сделать, поскольку это не является частью общедоступного API класса NSURLConnection.

Комментарии:

1. «Однако я думаю, что для вызываемого абонента было бы довольно удивительно, если бы я изменил исходное поведение класса и предпочел бы этого не делать». — разве это не именно то, что вы делаете с Javascript?

2. Нет. Я использую исходный делегат в качестве прототипа для оформленного делегата, т. Е. Каждый вызов метода для оформленного делегата будет вызывать исходный делегат, если он не перезаписан в оформленном делегате.