Qt 4.8
qgraph_p.h
Go to the documentation of this file.
1 /****************************************************************************
2 **
3 ** Copyright (C) 2014 Digia Plc and/or its subsidiary(-ies).
4 ** Contact: http://www.qt-project.org/legal
5 **
6 ** This file is part of the QtGui module of the Qt Toolkit.
7 **
8 ** $QT_BEGIN_LICENSE:LGPL$
9 ** Commercial License Usage
10 ** Licensees holding valid commercial Qt licenses may use this file in
11 ** accordance with the commercial license agreement provided with the
12 ** Software or, alternatively, in accordance with the terms contained in
13 ** a written agreement between you and Digia. For licensing terms and
14 ** conditions see http://qt.digia.com/licensing. For further information
15 ** use the contact form at http://qt.digia.com/contact-us.
16 **
17 ** GNU Lesser General Public License Usage
18 ** Alternatively, this file may be used under the terms of the GNU Lesser
19 ** General Public License version 2.1 as published by the Free Software
20 ** Foundation and appearing in the file LICENSE.LGPL included in the
21 ** packaging of this file. Please review the following information to
22 ** ensure the GNU Lesser General Public License version 2.1 requirements
23 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
24 **
25 ** In addition, as a special exception, Digia gives you certain additional
26 ** rights. These rights are described in the Digia Qt LGPL Exception
27 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
28 **
29 ** GNU General Public License Usage
30 ** Alternatively, this file may be used under the terms of the GNU
31 ** General Public License version 3.0 as published by the Free Software
32 ** Foundation and appearing in the file LICENSE.GPL included in the
33 ** packaging of this file. Please review the following information to
34 ** ensure the GNU General Public License version 3.0 requirements will be
35 ** met: http://www.gnu.org/copyleft/gpl.html.
36 **
37 **
38 ** $QT_END_LICENSE$
39 **
40 ****************************************************************************/
41 
42 #ifndef QGRAPH_P_H
43 #define QGRAPH_P_H
44 
45 //
46 // W A R N I N G
47 // -------------
48 //
49 // This file is not part of the Qt API. It exists purely as an
50 // implementation detail. This header file may change from version to
51 // version without notice, or even be removed.
52 //
53 // We mean it.
54 //
55 
56 #include <QtCore/QHash>
57 #include <QtCore/QQueue>
58 #include <QtCore/QString>
59 #include <QtCore/QDebug>
60 
61 #include <float.h>
62 
64 
65 template <typename Vertex, typename EdgeData>
66 class Graph
67 {
68 public:
69  Graph() {}
70 
72  public:
73  const_iterator(const Graph *graph, bool begin) : g(graph){
74  if (begin) {
75  row = g->m_graph.constBegin();
76  //test if the graph is empty
77  if (row != g->m_graph.constEnd())
78  {
79  column = (*row)->constBegin();
80  }
81  } else {
82  row = g->m_graph.constEnd();
83  }
84  }
85 
86  inline Vertex *operator*() {
87  return column.key();
88  }
89 
90  inline Vertex *from() const {
91  return row.key();
92  }
93 
94  inline Vertex *to() const {
95  return column.key();
96  }
97 
98  inline bool operator==(const const_iterator &o) const { return !(*this != o); }
99  inline bool operator!=(const const_iterator &o) const {
100  if (row == g->m_graph.end()) {
101  return row != o.row;
102  } else {
103  return row != o.row || column != o.column;
104  }
105  }
106  inline const_iterator& operator=(const const_iterator &o) const { row = o.row; column = o.column; return *this;}
107 
108  // prefix
110  if (row != g->m_graph.constEnd()) {
111  ++column;
112  if (column == (*row)->constEnd()) {
113  ++row;
114  if (row != g->m_graph.constEnd()) {
115  column = (*row)->constBegin();
116  }
117  }
118  }
119  return *this;
120  }
121 
122  private:
123  const Graph *g;
126  };
127 
129  return const_iterator(this,true);
130  }
131 
133  return const_iterator(this,false);
134  }
135 
143  EdgeData *edgeData(Vertex* first, Vertex* second) {
145  return row ? row->value(second) : 0;
146  }
147 
148  void createEdge(Vertex *first, Vertex *second, EdgeData *data)
149  {
150  // Creates a bidirectional edge
151 #if defined(QT_DEBUG) && 0
152  qDebug("Graph::createEdge(): %s",
154  .arg(first->toString()).arg(second->toString())));
155 #endif
156  if (edgeData(first, second)) {
157 #ifdef QT_DEBUG
158  qWarning("%s-%s already has an edge", qPrintable(first->toString()), qPrintable(second->toString()));
159 #endif
160  }
161  createDirectedEdge(first, second, data);
162  createDirectedEdge(second, first, data);
163  }
164 
165  void removeEdge(Vertex *first, Vertex *second)
166  {
167  // Removes a bidirectional edge
168 #if defined(QT_DEBUG) && 0
169  qDebug("Graph::removeEdge(): %s",
171  .arg(first->toString()).arg(second->toString())));
172 #endif
173  EdgeData *data = edgeData(first, second);
174  removeDirectedEdge(first, second);
175  removeDirectedEdge(second, first);
176  if (data) delete data;
177  }
178 
179  EdgeData *takeEdge(Vertex* first, Vertex* second)
180  {
181 #if defined(QT_DEBUG) && 0
182  qDebug("Graph::takeEdge(): %s",
184  .arg(first->toString()).arg(second->toString())));
185 #endif
186  // Removes a bidirectional edge
187  EdgeData *data = edgeData(first, second);
188  if (data) {
189  removeDirectedEdge(first, second);
190  removeDirectedEdge(second, first);
191  }
192  return data;
193  }
194 
195  QList<Vertex *> adjacentVertices(Vertex *vertex) const
196  {
199  if (row)
200  l = row->keys();
201  return l;
202  }
203 
205  QSet<Vertex *> setOfVertices;
206  for (const_iterator it = constBegin(); it != constEnd(); ++it) {
207  setOfVertices.insert(*it);
208  }
209  return setOfVertices;
210  }
211 
214  for (const_iterator it = constBegin(); it != constEnd(); ++it) {
215  Vertex *from = it.from();
216  Vertex *to = it.to();
217  // do not return (from,to) *and* (to,from)
218  if (from < to) {
219  conns.append(qMakePair(from, to));
220  }
221  }
222  return conns;
223  }
224 
225 #if defined(QT_DEBUG)
226  QString serializeToDot() { // traversal
227  QString strVertices;
228  QString edges;
229 
230  QSet<Vertex *> setOfVertices = vertices();
231  for (Q_TYPENAME QSet<Vertex*>::const_iterator it = setOfVertices.begin(); it != setOfVertices.end(); ++it) {
232  Vertex *v = *it;
233  QList<Vertex*> adjacents = adjacentVertices(v);
234  for (int i = 0; i < adjacents.count(); ++i) {
235  Vertex *v1 = adjacents.at(i);
236  EdgeData *data = edgeData(v, v1);
237  bool forward = data->from == v;
238  if (forward) {
239  edges += QString::fromAscii("\"%1\"->\"%2\" [label=\"[%3,%4,%5,%6,%7]\" color=\"#000000\"] \n")
240  .arg(v->toString())
241  .arg(v1->toString())
242  .arg(data->minSize)
243  .arg(data->minPrefSize)
244  .arg(data->prefSize)
245  .arg(data->maxPrefSize)
246  .arg(data->maxSize)
247  ;
248  }
249  }
250  strVertices += QString::fromAscii("\"%1\" [label=\"%2\"]\n").arg(v->toString()).arg(v->toString());
251  }
252  return QString::fromAscii("%1\n%2\n").arg(strVertices).arg(edges);
253  }
254 #endif
255 
256 protected:
257  void createDirectedEdge(Vertex *from, Vertex *to, EdgeData *data)
258  {
259  QHash<Vertex *, EdgeData *> *adjacentToFirst = m_graph.value(from);
260  if (!adjacentToFirst) {
261  adjacentToFirst = new QHash<Vertex *, EdgeData *>();
262  m_graph.insert(from, adjacentToFirst);
263  }
264  adjacentToFirst->insert(to, data);
265  }
266 
267  void removeDirectedEdge(Vertex *from, Vertex *to)
268  {
269  QHash<Vertex *, EdgeData *> *adjacentToFirst = m_graph.value(from);
270  Q_ASSERT(adjacentToFirst);
271 
272  adjacentToFirst->remove(to);
273  if (adjacentToFirst->isEmpty()) {
274  //nobody point to 'from' so we can remove it from the graph
275  m_graph.remove(from);
276  delete adjacentToFirst;
277  }
278  }
279 
280 private:
282 };
283 
285 
286 #endif
The QHash::const_iterator class provides an STL-style const iterator for QHash and QMultiHash...
Definition: qhash.h:395
#define QT_END_NAMESPACE
This macro expands to.
Definition: qglobal.h:90
static QString fromAscii(const char *, int size=-1)
Returns a QString initialized with the first size characters from the string str. ...
Definition: qstring.cpp:4276
int remove(const Key &key)
Removes all the items that have the key from the hash.
Definition: qhash.h:784
#define it(className, varName)
Definition: qgraph_p.h:66
Vertex * operator*()
Definition: qgraph_p.h:86
QList< QPair< Vertex *, Vertex * > > connections() const
Definition: qgraph_p.h:212
QSet< Vertex * > vertices() const
Definition: qgraph_p.h:204
const_iterator & operator++()
Definition: qgraph_p.h:109
int count(const T &t) const
Returns the number of occurrences of value in the list.
Definition: qlist.h:891
The QString class provides a Unicode character string.
Definition: qstring.h:83
The QHash class is a template class that provides a hash-table-based dictionary.
Definition: qdatastream.h:66
EdgeData * edgeData(Vertex *first, Vertex *second)
Definition: qgraph_p.h:143
void createEdge(Vertex *first, Vertex *second, EdgeData *data)
Definition: qgraph_p.h:148
#define Q_ASSERT(cond)
Definition: qglobal.h:1823
iterator begin()
Definition: qset.h:166
bool operator!=(const const_iterator &o) const
Definition: qgraph_p.h:99
const T value(const Key &key) const
Returns the value associated with the key.
Definition: qhash.h:606
iterator insert(const Key &key, const T &value)
Inserts a new item with the key and a value of value.
Definition: qhash.h:753
Q_CORE_EXPORT void qDebug(const char *,...)
Q_TYPENAME QHash< Vertex *, QHash< Vertex *, EdgeData * > *>::const_iterator row
Definition: qgraph_p.h:124
void append(const T &t)
Inserts value at the end of the list.
Definition: qlist.h:507
#define QT_BEGIN_NAMESPACE
This macro expands to.
Definition: qglobal.h:89
#define Q_TYPENAME
Definition: qglobal.h:1717
QHash< Vertex *, QHash< Vertex *, EdgeData * > * > m_graph
Definition: qgraph_p.h:281
QList< Vertex * > adjacentVertices(Vertex *vertex) const
Definition: qgraph_p.h:195
const T & at(int i) const
Returns the item at index position i in the list.
Definition: qlist.h:468
iterator end()
Definition: qset.h:169
bool isEmpty() const
Returns true if the hash contains no items; otherwise returns false.
Definition: qhash.h:297
Q_CORE_EXPORT void qWarning(const char *,...)
const_iterator insert(const T &value)
Definition: qset.h:179
static const char * data(const QByteArray &arr)
const_iterator constBegin() const
Returns a const STL-style iterator pointing to the first item in the hash.
Definition: qhash.h:466
const_iterator constEnd() const
Returns a const STL-style iterator pointing to the imaginary item after the last item in the hash...
Definition: qhash.h:469
const_iterator & operator=(const const_iterator &o) const
Definition: qgraph_p.h:106
QString arg(qlonglong a, int fieldwidth=0, int base=10, const QChar &fillChar=QLatin1Char(' ')) const Q_REQUIRED_RESULT
Definition: qstring.cpp:7186
iterator end()
Returns an STL-style iterator pointing to the imaginary item after the last item in the hash...
Definition: qhash.h:467
const Graph * g
Definition: qgraph_p.h:123
const Key key(const T &value) const
Returns the first key mapped to value.
Definition: qhash.h:674
Graph()
Definition: qgraph_p.h:69
Q_OUTOFLINE_TEMPLATE QPair< T1, T2 > qMakePair(const T1 &x, const T2 &y)
Definition: qpair.h:102
const_iterator(const Graph *graph, bool begin)
Definition: qgraph_p.h:73
QFactoryLoader * l
QString serializeToDot()
Definition: qgraph_p.h:226
EdgeData * takeEdge(Vertex *first, Vertex *second)
Definition: qgraph_p.h:179
void removeDirectedEdge(Vertex *from, Vertex *to)
Definition: qgraph_p.h:267
void removeEdge(Vertex *first, Vertex *second)
Definition: qgraph_p.h:165
#define qPrintable(string)
Definition: qglobal.h:1750
QList< Key > keys() const
Returns a list containing all the keys in the hash, in an arbitrary order.
Definition: qhash.h:648
Vertex * from() const
Definition: qgraph_p.h:90
Q_TYPENAME QHash< Vertex *, EdgeData * >::const_iterator column
Definition: qgraph_p.h:125
Vertex * to() const
Definition: qgraph_p.h:94
bool operator==(const const_iterator &o) const
Definition: qgraph_p.h:98
const_iterator constBegin() const
Definition: qgraph_p.h:128
The QList class is a template class that provides lists.
Definition: qdatastream.h:62
void createDirectedEdge(Vertex *from, Vertex *to, EdgeData *data)
Definition: qgraph_p.h:257
const_iterator constEnd() const
Definition: qgraph_p.h:132