1/* Copyright 2009, UCAR/Unidata and OPeNDAP, Inc.
2   See the COPYRIGHT file for more information. */
3#include <stdlib.h>
4#include <stdio.h>
5#include <string.h>
6
7#include "oclist.h"
8
9int oclistnull(void* e) {return e == NULL;}
10
11#ifndef TRUE
12#define TRUE 1
13#endif
14#ifndef FALSE
15#define FALSE 0
16#endif
17
18#define DEFAULTALLOC 16
19#define ALLOCINCR 16
20
21OClistoclistnew(void)
22{
23  OClistl;
24/*
25  if(!ocinitialized) {
26    memset((void*)&ocDATANULL,0,sizeof(void*));
27    ocinitialized = 1;
28  }
29*/
30  l = (OClist*)malloc(sizeof(OClist));
31  if(l) {
32    l->alloc=0;
33    l->length=0;
34    l->content=NULL;
35  }
36  return l;
37}
38
39int
40oclistfree(OClistl)
41{
42  if(l) {
43    l->alloc = 0;
44    if(l->content != NULL) {free(l->content); l->content = NULL;}
45    free(l);
46  }
47  return TRUE;
48}
49
50int
51oclistsetalloc(OClistl, size_t sz)
52{
53  void** newcontent = NULL;
54  if(l == NULL) return FALSE;
55  if(sz <= 0) {sz = (l->length?2*l->length:DEFAULTALLOC);}
56  if(l->alloc >= sz) {return TRUE;}
57  newcontent=(void**)calloc(sz,sizeof(void*));
58  if(newcontent != NULL && l->alloc > 0 && l->length > 0 && l->content != NULL) {
59    memcpy((void*)newcontent,(void*)l->content,sizeof(void*)*l->length);
60  }
61  if(l->content != NULL) free(l->content);
62  l->content=newcontent;
63  l->alloc=sz;
64  return TRUE;
65}
66
67int
68oclistsetlength(OClistl, size_t sz)
69{
70  if(l == NULL) return FALSE;
71  if(sz > l->alloc && !oclistsetalloc(l,sz)) return FALSE;
72  l->length = sz;
73  return TRUE;
74}
75
76void*
77oclistget(OClistl, size_t index)
78{
79  if(l == NULL || l->length == 0) return NULL;
80  if(index >= l->length) return NULL;
81  return l->content[index];
82}
83
84int
85oclistset(OClistl, size_t index, void* elem)
86{
87  if(l == NULL) return FALSE;
88  if(index >= l->length) return FALSE;
89  l->content[index] = elem;
90  return TRUE;
91}
92
93/* Insert at position i of l; will push up elements i..|seq|. */
94int
95oclistinsert(OClistl, size_t index, void* elem)
96{
97  int i; /* do not make unsigned */
98  if(l == NULL) return FALSE;
99  if(index > l->length) return FALSE;
100  oclistsetalloc(l,0);
101  for(i=(int)l->length;i>index;i--) l->content[i] = l->content[i-1];
102  l->content[index] = elem;
103  l->length++;
104  return TRUE;
105}
106
107int
108oclistpush(OClistl, void* elem)
109{
110  if(l == NULL) return FALSE;
111  if(l->length >= l->allococlistsetalloc(l,0);
112  l->content[l->length] = elem;
113  l->length++;
114  return TRUE;
115}
116
117void*
118oclistpop(OClistl)
119{
120  if(l == NULL || l->length == 0) return NULL;
121  l->length--;
122  return l->content[l->length];
123}
124
125void*
126oclisttop(OClistl)
127{
128  if(l == NULL || l->length == 0) return NULL;
129  return l->content[l->length - 1];
130}
131
132void*
133oclistremove(OClistl, size_t i)
134{
135  size_t len;
136  void* elem;
137  if(l == NULL || (len=l->length) == 0) return NULL;
138  if(i >= len) return NULL;
139  elem = l->content[i];
140  for(i+=1;i<len;i++) l->content[i-1] = l->content[i];
141  l->length--;
142  return elem;
143}
144
145/* Duplicate and return the content (null terminate) */
146void**
147oclistdup(OClistl)
148{
149    void** result = (void**)malloc(sizeof(void*)*(l->length+1));
150    if(result != NULL) {
151 if(l != NULL && oclistlength(l) != 0)
152            memcpy((void*)result,(void*)l->content,sizeof(void*)*l->length);
153        result[l->length] = (void*)0;
154    }
155    return result;
156}
157
158int
159oclistcontains(OClistl, void* elem)
160{
161    size_t i;
162    for(i=0;i<oclistlength(l);i++) {
163 if(elem == oclistget(l,i)) return 1;
164    }
165    return 0;
166}
167
168/* Remove element by value; only removes first encountered */
169int
170oclistelemremove(OClistl, void* elem)
171{
172  size_t len;
173  size_t i;
174  int found = 0;
175  if(l == NULL || (len=l->length) == 0) return 0;
176  for(i=0;i<oclistlength(l);i++) {
177    void* candidate = l->content[i];
178    if(elem == candidate) {
179      for(i+=1;i<len;i++) l->content[i-1] = l->content[i];
180      l->length--;
181      found = 1;
182      break;
183    }
184  }
185  return found;
186}
187
188
189
190
191/* Extends oclist to include a unique operator
192   which remove duplicate values; NULL values removed
193   return value is always 1.
194*/
195
196int
197oclistunique(OClistl)
198{
199    size_t i,j,k,len;
200    void** content;
201    if(l == NULL || l->length == 0) return 1;
202    len = l->length;
203    content = l->content;
204    for(i=0;i<len;i++) {
205        for(j=i+1;j<len;j++) {
206     if(content[i] == content[j]) {
207 /* compress out jth element */
208                for(k=j+1;k<len;k++) content[k-1] = content[k];
209 len--;
210     }
211 }
212    }
213    l->length = len;
214    return 1;
215}
216
217OClist*
218oclistclone(OClistl)
219{
220    OClistclone = oclistnew();
221    *clone = *l;
222    clone->content = oclistdup(l);
223    return clone;
224}


HyperKWIC - Version 7.20DA executed at 11:37 on 27 Oct 2017 | Polyhedron Solutions - INTERNAL USE | COMMERCIAL (Any O/S) SN 4AKIed