Документ взят из кэша поисковой машины. Адрес
оригинального документа
: http://rtm-cs.sinp.msu.ru/manual/qt/collection.html
Дата изменения: Sun Jul 12 02:59:00 1998 Дата индексирования: Mon Oct 1 20:26:55 2012 Кодировка: |
A collection class is a class that can contain a number of items in a certain data structure and perform operations on the contained items; insert, remove, find etc.
Qt has many collection classes:
Some of these classes have corresponding iterators. An iterator is a class for safely traversing the items in a collection:
The collection classes work with pointers to items. Qt has an array template class, QArray, which stores the items directly in the array. QArray only works for classes that do not have a constructor, a destructor or any virtual functions.
Basically, there are two different implementation strategies for collection classes.
In Qt, we have chosen the second approach. There are three internal base
classes; QGCache, QGDict and
QGList that operate on void*
pointers. A thin
template layer implements the actual collections by casting item pointers
to and from void*.
Some compilers do not support C++ templates. For these compilers, we have implemented macro expansions that emulate templates.
This example shows how to store Employee items in a list and prints them out in the reverse order:
#include <qlist.h> #include <qstring.h> #include <stdio.h> class Employee { public: Employee( const char *name, int salary ) { n=name; s=salary; } const char *name() const { return n; } int salary() const { return s; } private: QString n; int s; }; void main() { QList<Employee> list; // list of pointers to Employee list.setAutoDelete( TRUE ); // delete items when they are removed list.append( new Employee("Bill", 50000) ); list.append( new Employee("Steve",80000) ); list.append( new Employee("Ron", 60000) ); QListIterator<Employee> it(list); // iterator for employee list for ( it.toLast(); it.current(); --it) ) { Employee *emp = it.current(); printf( "%s earns %d\n", emp->name(), emp->salary() ); } }
Program output:
Ron earns 60000 Steve earns 80000 Bill earns 50000
All collections inherit the QCollection base class. This class knows only the number of items in the collection and the delete strategy.
Items in a collection are by default not deleted when they are removed from the collection. The QCollection::setAutoDelete() function specifies the delete strategy. In the list example, we enable auto-deletion to make the list delete the items when they are removed from the list.
When inserting an item into a collection, only the pointer is copied, not the item itself. This is called a shallow copy. It is possible to make the collection copy all of the item's data (known as a deep copy) when an item is inserted. All collection functions that insert an item call the virtual function QCollection::newItem() for the item to be inserted. Inherit a collection and reimplement it if you want to have deep copies in your collection.
When removing an item from a list, the virtual function QCollection::deleteItem() is called. The default implementation in all collection classes is to delete the item if auto-deletion is enabled.
A template-based collection, for instance QList<type>, defines a collection of pointers to type objects. The pointer (*) is implicit.
We discuss QList here, but the same applies for all collection classes and all collection class iterators.
Template instantiation:
QList<Employee> list; // wherever the list is used
The item's class or type, Employee in our example, must be defined prior to the list definition.
// Does not work: Employee is not defined class Employee; QList<Employee> list; // This works: Employee is defined before it is used class Employee { ... }; QList<Employee> list;
The list can also be instantiated through a macro expansion. This is necessary only for compilers that do not support templates.
Macro instantiation:
Q_DECLARE(QListM,Employee); // declare once (for instance in a .h file) ... QListM(Employee) list; // wherever the list is used
If you want to make your code work for compilers that do not have
template support, but use templates if they are available, you
can use typedef:
... #if defined(USE_TEMPLATECLASS) typedef QListT<Employee> EmployeeList; #else typedef Q_DECLARE(QListM,Employee) EmployeeList; #endif void main() { EmployeeList list; // list of pointers to Employee ...
USE_TEMPLATECLASS
is defined in qglobal.h.
QListT refers to the QList template and QListM refers to the QList macro. QList defaults to QListT if templates are supported, QListM otherwise.
We recommend using templates, because macro collections are harder to debug. C++ debuggers understand templates but not macros.
Although QList has member functions to traverse the list, it can often be better to make use of an iterator. QListIterator is very safe and can traverse lists that are being modified at the same time. Multiple iterators can work independently on the same collection.
A QList has an internal list of all iterators that are currently operating on the list. When a list entry is removed, the list updates all iterators to point to this entry.
The QDict and QCache collections have no traversal functions. To traverse the these collections, you must use QDictIterator or QCacheIterator .
Qt has the following predefined collection classes:
Classes:
char*
keys)
char*
keys)
long
keys)
long
keys)
void*
keys)
char*
with case insensitive compare)
char*.
)
Copyright © 1998 Troll Tech | Trademarks | Qt version 1.40
|