Утечка памяти в структурах Swift. Как это исправить?

Я разрабатываю приложение в Swift 2 (Xcode 7 beta 3), и, когда это возможно, я пытаюсь использовать типы значений (структуры и перечисления). Согласно документации Apple относительно управления памятью, работа с типами значений не должна вызывать каких-либо циклов сохранения, и она должна просто работать.

Но сегодня я столкнулся с огромным количеством утечек памяти в коде обработки событий. Я отследил его и уменьшил проблему до следующего минимального примера.

Предположим, что существует элемент протокола, который определяет одно value свойства:

 protocol Item { var value: String { get } } 

Затем мы создаем конкретную структуру, которая реализует протокол Item и добавляет дополнительное свойство additionalValue . Назовем struct FooItem .

 struct FooItem<T>: Item { let value: String let additionalValue: T init(value: String, additionalValue: T) { self.value = value self.additionalValue = additionalValue } } 

Третья часть головоломки – это другая структура, которая обертывает элемент, реализующий протокол Item . Это называется ItemWrapper .

 struct ItemWrapper { let item: Item init(item: Item) { self.item = item } } 

Если в приложении «Инструменты» используется конфигурация «Утечки памяти», утечка памяти появляется каждый раз, ItemWrapper значение ItemWrapper создается с помощью FooItem .

 let item = FooItem(value: "protocol value", additionalValue: "foo item value") let _ = ItemWrapper(item: item) 

Инструменты скриншот 1Инструменты скриншот 2

Вот пример проекта Xcode и файла Instruments : https://www.dropbox.com/s/z6ugxzxqggrv1xl/SwiftStructsMemoryLeak.zip?dl=0

Весь пример кода можно просмотреть в этом Gist: https://gist.github.com/lukaskubanek/4e3f7657864103d79e3a

Вот отчет об ошибке: rdar: // 21375421

Это ошибка в компиляторе Swift, или я делаю что-то неправильно?


EDIT 1 : Как было предложено в комментариях, я перепробовал этот вопрос на форуме Apple Dev , чтобы привлечь больше внимания со стороны сообщества Swift и, возможно, от разработчиков языка. Из-за миграции форумов dev во время WWDC 2015 я должен был опубликовать обновленный вопрос на новых форумах. Вот ссылка: https://forums.developer.apple.com/message/9643


EDIT 2 : Проблема, которую я изначально разместил в примере кода, кажется, разрешена в Swift 2.0 . Поскольку это не решило проблемы в моем приложении, я сделал еще одну модификацию кода примера. Теперь дополнительное свойство FooItem имеет общий тип, а FooItem аннотируется типом и, следовательно, общим типом. Вот как я использую его в своем приложении, и он по-прежнему вызывает утечку памяти, но на этот раз, когда ItemWrapper инициализируется, а не при доступе к свойству.


РЕДАКТИРОВАТЬ 3 : Полностью обновить вопрос к модифицированной проблеме, которая сохраняется в Swift 2.0 и загружена новая версия проекта Xcode.

2 Solutions collect form web for “Утечка памяти в структурах Swift. Как это исправить?”

Хотя у меня нет ответа от Apple ни на форумах разработчиков, ни в трекерах по ошибкам, и я не нашел ничего связанного с этой проблемой в примечаниях к выпуску последних бета-версий, это похоже на решение в компиляторе Swift в Xcode 7 beta 5 . (Возможно, он также работает в бета-версии 4. Последняя версия, которую я проверил, была бета-версией 3.)

Демонстрационный проект больше не создает утечку памяти. То же самое верно для моего приложения. Ура!

введите описание изображения здесь

Ну, вот обходной путь, хотя я понятия не имею, почему это работает. Я заметил, что если вы это сделаете:

  let theItem = itemWrapper.item let value = theItem.value 

…вместо этого:

  let value = itemWrapper.item.value 

… он не генерирует утечку памяти.

  • Не удается архивировать проект эпохи iOS 5.0 с помощью RestKit v0.10.3 с использованием Xcode 7.2
  • Ошибка тестирования пользовательского интерфейса - Ошибка получения моментального снимка для элемента Ошибка -25201
  • Xcode 7 шрифт iOS9 больше не распознается
  • Xcode7: libGGLAnalytics.a (GGLContext + Analytics.o) 'не содержит биткода
  • Xcode 7 GM Seed - не удается отправить в App Store для обзора
  • FFMpeg на iOS Swift
  • Я создал одно расширение строки для объединения строки с пространством в swift 2.0, но не работает в swift 2.1 xcode 7
  • Xcode 7 UI Testing: как отклонить ряд системных предупреждений в коде
  • Swift 2 - Не удается получить местоположение пользователя с помощью CLLocationManager
  • Как удалить серую нижнюю панель в iPad-симуляторе
  • ERROR ITMS-90085: «Никаких архитектур в двоичном формате. Lipo не удалось обнаружить какие-либо архитектуры в исполняемом пакете ».
  • Interesting Posts

    AWSCognito забыли пароль, не работающий на не подтвержденный номер мобильного телефона iOS

    Странное перекрытие элементов в iOS (PhoneGap)

    Firebase QueryOrderedByChild вместе с EqualToValue и StartingAtValue Combination

    Плагин для покупки приложений (IAP) для PhoneGap 2.0 на iOS?

    Чтение длинных значений характеристик с помощью CoreBluetooth

    есть ли способ сделать снимок экрана при воспроизведении MPMoviePlayerController

    UIView неожиданно переходит в строку состояния

    Сетевой адаптер связи на 100% потерю пакетов – почему я неправильно получаю статус доступности Интернета?

    прерывистый extaudiofileread exc_bad_access

    Несбалансированные вызовы для перехода на начало / конец для <FirstViewController: 0x2a2c00>

    WKWebView не откроет внешние ссылки

    Контейнер представления IOS: как установить делегат

    Доступ к iOS 7 скрыт UITableViewCellScrollView?

    Каков размер изображения (разрешение) для разработки приложений iPad 3?

    CS193P Назначение 3, подсказка № 5 – Какова модель?

    PhoneC: Разработка iOS проста с помощью XCode, Swift3, UITableView, cocatouch, давайте создадим приложения для iPhone, iPad и Macbook.