Skip to content

Commit 75a0754

Browse files
committedJul 1, 2013
Initial Commit
0 parents  commit 75a0754

File tree

9 files changed

+285
-0
lines changed

9 files changed

+285
-0
lines changed
 

‎.gitignore

+2
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
*swp
2+
*pyc

‎Makefile

+16
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
CC=g++
2+
CFLAGS=-g -ggdb -Wall -Iinclude
3+
LDFLAGS= -lm
4+
OBJECTS=src/test.o
5+
6+
all: src/test
7+
8+
src/test: $(OBJECTS)
9+
$(CC) -o $@ $(LDFLAGS) $(OBJECTS)
10+
11+
$(OBJECTS): %.o: %.cpp
12+
$(CC) -o $@ $(CFLAGS) -c $<
13+
14+
clean:
15+
rm -rf src/*.o
16+
rm -rf src/test

‎cpppython/__init__.py

Whitespace-only changes.

‎cpppython/hash.py

+33
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
#!/usr/bin/env python
2+
try:
3+
import numpy as np
4+
has_np=True
5+
except ImportError:
6+
has_np=False
7+
8+
def hash_any(value, hv=None):
9+
hv = hv or 0
10+
if value is None or isinstance(value, (str, unicode, int, long, float, bool)):
11+
# log.debug('is primitive: value=%s hv=%s', value, hv)
12+
hv = hash(value) ^ hv
13+
elif has_np and np.isscalar(value):
14+
# log.debug('is numpy.scalar: value=%s hv=%s', value, hv)
15+
hf = hash(value) ^ hv
16+
elif isinstance(value, (list, tuple, set)):
17+
# log.debug('is list/tuple/set: value=%s hv=%s', value, hv)
18+
for x in value:
19+
hv = hash_any(x, hv)
20+
elif isinstance(value, dict):
21+
# log.debug('is dict: value=%s hv=%s', value, hv)
22+
for k,v in value.iteritems():
23+
hv = hash_any(k, hv)
24+
hv = hash_any(v, hv)
25+
elif isinstance(value, slice):
26+
# Hash a tuple of the slice components
27+
hv = hash((value.start, value.stop, value.step)) ^ hv
28+
elif isinstance(value, object):
29+
# log.debug('is object: value=%s hv=%s', value, hv)
30+
hv = hash_any(value.__dict__, hv)
31+
32+
return hv
33+

‎cpppython/linked_list.pyx

+54
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
from cython.operator cimport dereference as dref
2+
from libc.stdlib cimport malloc, free
3+
from cpppython.hash import hash_any
4+
5+
cdef extern from "linked_list.h":
6+
cdef cppclass LinkedList[T]:
7+
LinkedList()
8+
size_t add(T element)
9+
size_t length()
10+
T pop() except +
11+
void remove(size_t i) except +
12+
T get(size_t i) except +
13+
14+
15+
16+
17+
cdef class PyLinkedList:
18+
cdef LinkedList[long int] *thisptr
19+
store = {}
20+
def __cinit__(self):
21+
self.thisptr = new LinkedList[long int]()
22+
def __dealloc__(self):
23+
del self.thisptr
24+
25+
def add(self, element):
26+
cdef long int key = hash_any(element)
27+
self.store[<object> key] = element
28+
self.thisptr.add(key)
29+
30+
def length(self):
31+
return <object> self.thisptr.length()
32+
33+
def pop(self):
34+
cdef long int key = self.thisptr.pop()
35+
retval = self.store[<object> key]
36+
del self.store[<object> key]
37+
return retval
38+
39+
def remove(self, i):
40+
self.thisptr.remove(<size_t> i)
41+
42+
def get(self, i):
43+
cdef long int key = self.thisptr.get(i)
44+
return self.store[<object> key]
45+
46+
def __len__(self):
47+
return <object> self.thisptr.length()
48+
49+
def __getitem__(self, i):
50+
if i<0:
51+
return self.get(len(self) + i)
52+
return self.get(i)
53+
54+

‎include/linked_list.h

+124
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,124 @@
1+
#ifndef __NODE_H__
2+
#define __NODE_H__
3+
4+
#include <iostream>
5+
#include <stdexcept>
6+
7+
template <class T>
8+
struct _LNode {
9+
T element;
10+
_LNode *next;
11+
};
12+
13+
14+
template <class T>
15+
class LinkedList {
16+
private:
17+
struct _LNode<T> *root;
18+
size_t elements;
19+
public:
20+
LinkedList();
21+
~LinkedList();
22+
23+
size_t add(T element);
24+
size_t length();
25+
T pop();
26+
T get(size_t i);
27+
void remove(size_t i);
28+
};
29+
30+
template <class T>
31+
LinkedList<T>::LinkedList()
32+
: root(NULL), elements(0)
33+
{
34+
}
35+
36+
template <class T>
37+
LinkedList<T>::~LinkedList() {
38+
struct _LNode<T> *p;
39+
struct _LNode<T> *tmp;
40+
p = root;
41+
while(p) {
42+
tmp = p;
43+
p = p->next;
44+
delete tmp;
45+
}
46+
};
47+
48+
49+
template <class T>
50+
size_t LinkedList<T>::add(T element) {
51+
struct _LNode<T> *p;
52+
if(!root) {
53+
root = new struct _LNode<T>;
54+
root->element = element;
55+
root->next = NULL;
56+
return ++elements;
57+
}
58+
p = root;
59+
while(p->next)
60+
p = p->next;
61+
62+
p->next = new struct _LNode<T>;
63+
p = p->next;
64+
p->element = element;
65+
p->next = NULL;
66+
return ++elements;
67+
}
68+
69+
template <class T>
70+
size_t LinkedList<T>::length() {
71+
return elements;
72+
}
73+
74+
template <class T>
75+
T LinkedList<T>::pop() {
76+
struct _LNode<T> *p;
77+
struct _LNode<T> *tmp;
78+
T retval;
79+
if(elements <= 0) {
80+
throw std::out_of_range("No elements to pop");
81+
}
82+
tmp = p = root;
83+
while(tmp->next) {
84+
p = tmp;
85+
tmp = tmp->next;
86+
}
87+
retval = tmp->element;
88+
p->next = NULL;
89+
delete tmp;
90+
elements--;
91+
return retval;
92+
}
93+
94+
95+
template <class T>
96+
T LinkedList<T>::get(size_t i) {
97+
struct _LNode<T> *p;
98+
if(i >= elements) {
99+
throw std::out_of_range("Index is out of range");
100+
}
101+
p = root;
102+
for(size_t j=0;j<i;j++)
103+
p = p->next;
104+
return p->element;
105+
}
106+
107+
template <class T>
108+
void LinkedList<T>::remove(size_t i) {
109+
struct _LNode<T> *p;
110+
struct _LNode<T> *tmp;
111+
if(i >= elements) {
112+
throw std::out_of_range("Index is out of range");
113+
}
114+
p = root;
115+
for(size_t j=0;j<i;j++) {
116+
tmp = p;
117+
p = p->next;
118+
}
119+
tmp->next = p->next;
120+
delete p;
121+
elements--;
122+
}
123+
124+
#endif /* __NODE_H__ */

‎setup.py

+20
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
#!/usr/bin/env python
2+
from setuptools import setup, find_packages
3+
from distutils.extension import Extension
4+
5+
import sys
6+
7+
if 'setuptools.extension' in sys.modules:
8+
m = sys.modules['setuptools.extension']
9+
m.Extension.__dict__ = m._Extension.__dict__
10+
11+
packages = find_packages()
12+
13+
linked_list_extension = Extension('cpppython.linked_list', ['cpppython/linked_list.pyx'],include_dirs=['include/'], language='c++')
14+
15+
setup(name='cpptest',
16+
version='0.0.1',
17+
packages=packages,
18+
setup_requires=['setuptools_cython'],
19+
ext_modules=[linked_list_extension],
20+
)

‎src/.gitkeep

Whitespace-only changes.

‎src/test.cpp

+36
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
#include <iostream>
2+
#include "linked_list.h"
3+
4+
using namespace std;
5+
6+
int main(int argc, char *argv[])
7+
{
8+
int a = 20;
9+
int tmp;
10+
LinkedList<int> list;
11+
list.add(a);
12+
cout << "Size: " << list.length() << endl;
13+
cout << "l[0] = " << list.get(0) << endl;
14+
cout << "l.pop() = " << list.pop() << endl;
15+
cout << "Size: " << list.length() << endl;
16+
try {
17+
cout << "Trying to get an element (should fail)"<<endl;
18+
tmp = list.get(0);
19+
cout << "Shouldn't see this" << endl;
20+
} catch(std::out_of_range& e) {
21+
cout << "Error: " << e.what() << endl;
22+
}
23+
for(int i=0;i<20;i++) {
24+
list.add(i);
25+
}
26+
27+
list.remove(10);
28+
29+
while(list.length() > 0)
30+
cout << list.pop() << " ";
31+
cout << endl;
32+
33+
34+
35+
return 0;
36+
}

0 commit comments

Comments
 (0)
Please sign in to comment.