File: wvlinklist.cc

package info (click to toggle)
wvstreams 4.0.2-4
  • links: PTS
  • area: main
  • in suites: sarge
  • size: 6,420 kB
  • ctags: 6,518
  • sloc: cpp: 52,544; sh: 5,770; ansic: 810; makefile: 461; tcl: 114; perl: 18
file content (111 lines) | stat: -rw-r--r-- 2,358 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
/*
 * Worldvisions Weaver Software:
 *   Copyright (C) 1997-2002 Net Integration Technologies, Inc.
 * 
 * Implementation of a Linked List management class, or rather, macros that
 * declare arbitrary linked list management classes.
 * 
 * wvlinklist.h does all the real work.
 */
#include "wvlinklist.h"

WvLink::WvLink(void *_data, WvLink *prev, WvLink *&tail, bool _auto_free,
	       char *_id)
{
    data = _data;
    next = prev->next;
    if (!next) tail = this;
    prev->next = this;
    auto_free = (unsigned)_auto_free;
    id = _id;
}


size_t WvListBase::count() const
{
    WvLink *l;
    size_t n = 0;
    
    for (l = head.next; l; l = l->next)
	n++;
    return n;
}


void WvListBase::reverse()
{
    WvLink *prev, *curr, *next;

    if (!head.next || !head.next->next)
        return;
    
    prev = head.next;
    curr = prev->next; 
   
    do {
        next = curr->next;
	curr->next = prev;
	prev = curr;
	curr = next;
    } while(curr);
    
    tail = head.next;
    tail->next = NULL;
    head.next = prev;
}


WvLink *WvListBase::IterBase::find(const void *data)
{
    for (rewind(); next(); )
    {
	if (link->data == data)
	    break;
    }
    
    return link;
}


#if 0
static WvListBase::SorterBase::CompareFunc *actual_compare = NULL;

static int magic_compare(const void *_a, const void *_b)
{
    WvLink *a = *(WvLink **)_a, *b = *(WvLink **)_b;
    return actual_compare(a->data, b->data);
}

void WvListBase::SorterBase::rewind(CompareFunc *cmp)
{
    if (array)
        delete array;
    array = lptr = NULL;

    int n = list->count();
    array = new WvLink * [n+1];
    WvLink **aptr = array;

    // fill the array with data pointers for sorting, so that the user doesn't
    // have to deal with the WvLink objects.  Put the WvLink pointers back 
    // in after sorting.
    IterBase i(*list);
    aptr = array;
    for (i.rewind(); i.next(); )
    {
        *aptr = i.cur();
        aptr++;
    }
    
    *aptr = NULL;

    // sort the array.  "Very nearly re-entrant" (unless the compare function
    // ends up being called recursively or something really weird...)
    CompareFunc *old_compare = actual_compare;
    actual_compare = cmp;
    qsort(array, n, sizeof(WvLink *), magic_compare);
    actual_compare = old_compare;

    lptr = NULL;    // subsequent next() will set it to first element.
}
#endif