Почему я должен использовать TCollections.CreateList<T>, а не TList<T>.Create
Я добавил map(), lower () и where(qlint: string) к моей развилке Spring4D. Когда я программировал эти функции, я обнаружил, что есть различия в поведении списков, когда они создаются по-разному.
Если я создаю их с TList<TSomeClass>.create
объекты в перечислимых типах TSomeClass
,
Если я создаю их с TCollections.CreateList<TSomeClass>
объекты в перечислимых типах TObject
,
Итак, вопрос:
Есть ли обратная сторона при использовании TList<TSomeClass>.create
?
Или другими словами: почему я должен использовать TCollections.CreateList<TSomeClass>
?
Кстати: с TCollections.CreateList я получил TObjectList, а не TList. Так что он должен называться TCollections.CreateObjectList... но это другая история.
1 ответ
В зависимости от версии компилятора многие из Spring.Collections.TCollections.Create
методы применяют то, на что не способен компилятор: складывать реализацию только в очень тонкий универсальный класс. Некоторые методы делают это с XE, некоторые только с XE7 (GetTypeKind
встроенная функция позволяет делать разрешение типов во время компиляции - см. параметр без параметров TCollections.CreateList<T>
например).
Это значительно уменьшает размер двоичного файла, если вы создаете много разных типов IList<T>
(где T - классы или интерфейсы), потому что это сворачивает их в TFolded(Object|Interface)List<T>
, Однако через интерфейс вы получаете доступ к элементам так, как вы их указали, а также к ElementType
свойство возвращает правильный тип и не только TObject
или же IInterface
, В Берлине он добавляет менее 1 КБ для каждого другого списка объектов, в то время как он добавляет около 80 КБ, если свертывание не применяется из-за всех внутренних классов, используемых для различных операций, которые вы можете вызывать IList<T>
,
Что касается TCollections.CreateList<T>
возвращая IList<T>
что поддерживается TFoldedObjectList<T>
когда T является классом, который полностью соответствует заданному. Так как OwnsObject
был принят как False
он имеет точно такое же поведение, как TList<T>
,
Коллекции Spring4D основаны на интерфейсе, поэтому не имеет значения, какой класс находится за интерфейсом, если он ведет себя в соответствии с контрактом интерфейса.
Убедитесь, что вы носите списки только как IList<T>
и не TList<T>
- вы можете создать их обоими способами (с теми преимуществами, которые я упоминал ранее при использовании TCollections
методы). В нашем собственном приложении некоторые места все еще используют конструктор классов, в то время как во многих других местах используются статические методы из Spring.Collections.TCollections
,
КСТАТИ:
Я видел активность в вашем форке и в imo нет необходимости реализовывать Map/Reduce, потому что она уже есть. Поскольку коллекции Spring4D моделируются после.NET, они называются Select
а также Aggregate
(увидеть Spring.Collections.TEnumerable
). Они не доступны на IEnumerable<T>
напрямую, потому что интерфейсы не должны иметь общих параметризованных методов.