Горячая замена кода в Xcode?
Я занимаюсь разработкой игр для iOS с использованием каркаса cocos2d, и я очень завидую возможности программистов Eclipse Java оперативно менять свой код во время отладки приложения (т. Е. Изменять значения переменных внутри метода и обновлять программу в режиме реального времени, как будто вы был REPL без перекомпиляции).
Это кажется чем-то очень полезным, когда дело доходит до разработки под iOS, где моя среда разработки (очевидно) - Xcode, а язык, на котором я программирую, - это Цель C. Я гуглил, но не смог ничего найти - так Я думал, что спрошу сообщество.
Кто-нибудь знает, есть ли способ горячей замены кода в Xcode при программировании в Objective C?
заранее спасибо
4 ответа
Невозможно с текущими инструментами.
Имейте в виду, что приложения для iOS подписаны - если вы измените один байт, вы все равно уйдете в отставку. Можно представить, как он работает, используя динамическую поддержку для динамического добавления и удаления методов. Но для этого наверняка потребовалось бы добавить некоторые дополнительные материалы для поддержки этого на устройстве, и это то, чем вредоносное ПО могло бы легко воспользоваться. Так что это, вероятно, не та функция, которую вы, вероятно, увидите в ближайшее время.
Кстати, в версиях Xcode 1.x-3.x была функция "Исправить и продолжить". Вы можете редактировать во время отладки, использовать команду "Исправить и продолжить" и продолжить запуск обновленного кода. Я считаю, что он был удален в какой-то момент, возможно, из-за некоторой комбинации: требования, чтобы ваш проект был настроен на использование "нулевой ссылки" и, возможно, некоторых других вещей; быть менее чем полностью надежным; вероятно, не поддерживает iOS; переключатель на llvm; другие изменения в Xcode 4. Может быть, он когда-нибудь вернется - если вы хотите вернуть его, сообщите об ошибке - но опять же, я думаю, что поддержка его на iOS будет проблемой.
Есть отличный плагин, который позволяет менять код в живом, работающем приложении. Это называется InjectionPlugin.
Как часто задаваемые вопросы говорит:
Как это работает? Среда выполнения Objective C позволяет вам загружать новую версию класса в приложение, используя пакет, даже если уже есть реализация, связанная с приложением. Swizzling используется при загрузке пакета для переключения существующего класса на использование методов новой реализации. Это может быть сделано несколько раз и работает для приложений OSX и iOS и на устройствах iOS.
Я сделал небольшое видео, которое показывает, как установить и использовать этот плагин http://nomtek.com/developers/how-to-install-and-use-injection-plugin-for-xcode/
Надеюсь, поможет!
Если вы просто говорите об изменении значений переменных, то можете достичь этого тайно через lldb (или, предположительно), gdb. Предположим, у вас было:
- (void)uselessMethod
{
NSString *localString = @"I'm some local text";
NSLog(@"%@", localString);
}
И поставить точку останова на NSLog
, в этот момент вы можете попросить lldb оценить переназначение localString как средства его выполнения. Например
po localString = @"Hat"
Если вы затем продолжите выполнение программы, вы обнаружите, что переназначение застряло. Точно так же вы можете вызвать любой метод или выполнить любое другое назначение.
Я только что проверил это с Xcode 4.3.2.
Вы можете выполнить горячую замену значения переменной в Xcode следующим образом:
expression <variable> = <value>;
,
Наличие точки останова в том месте, где вы хотите изменить значение, и выполнение команды в консоли XCode.
Пример:
// Messages From Console
(lldb) expression graphFlag = @"X"; // Update variable value
(__NSCFConstantString *) $0 = 0x36f95718 @"X" // Xcode prints the updated value
(lldb) expression graphFlag; // Printing value through expression command
(__NSCFConstantString *) $1 = 0x36f95718 @"X" // Hot Swapped variable value