Commit f454bb8d authored by Kevin Modzelewski's avatar Kevin Modzelewski

stdlib improvements

- int(bool) works
- hash(bool) works
- str.find() now takes an optional "start" parameter
parent 3dfe6311
...@@ -48,6 +48,10 @@ extern "C" Box* boolRepr(BoxedBool* v) { ...@@ -48,6 +48,10 @@ extern "C" Box* boolRepr(BoxedBool* v) {
return boxStrConstant("False"); return boxStrConstant("False");
} }
extern "C" Box* boolHash(BoxedBool* v) {
return boxInt(v == True);
}
extern "C" Box* boolNew(Box* cls, Box* val) { extern "C" Box* boolNew(Box* cls, Box* val) {
assert(cls == bool_cls); assert(cls == bool_cls);
...@@ -64,6 +68,7 @@ void setupBool() { ...@@ -64,6 +68,7 @@ void setupBool() {
bool_cls->giveAttr("__nonzero__", new BoxedFunction(boxRTFunction((void*)boolNonzero, BOXED_BOOL, 1))); bool_cls->giveAttr("__nonzero__", new BoxedFunction(boxRTFunction((void*)boolNonzero, BOXED_BOOL, 1)));
bool_cls->giveAttr("__repr__", new BoxedFunction(boxRTFunction((void*)boolRepr, STR, 1))); bool_cls->giveAttr("__repr__", new BoxedFunction(boxRTFunction((void*)boolRepr, STR, 1)));
bool_cls->giveAttr("__str__", bool_cls->getattr("__repr__")); bool_cls->giveAttr("__str__", bool_cls->getattr("__repr__"));
bool_cls->giveAttr("__hash__", new BoxedFunction(boxRTFunction((void*)boolHash, BOXED_INT, 1)));
bool_cls->giveAttr("__new__", bool_cls->giveAttr("__new__",
new BoxedFunction(boxRTFunction((void*)boolNew, UNKNOWN, 2, 1, false, false), { None })); new BoxedFunction(boxRTFunction((void*)boolNew, UNKNOWN, 2, 1, false, false), { None }));
......
...@@ -26,6 +26,7 @@ ...@@ -26,6 +26,7 @@
#include "core/ast.h" #include "core/ast.h"
#include "core/types.h" #include "core/types.h"
#include "gc/collector.h" #include "gc/collector.h"
#include "runtime/classobj.h"
#include "runtime/ics.h" #include "runtime/ics.h"
#include "runtime/import.h" #include "runtime/import.h"
#include "runtime/inline/xrange.h" #include "runtime/inline/xrange.h"
...@@ -339,6 +340,10 @@ Box* isinstance_func(Box* obj, Box* cls) { ...@@ -339,6 +340,10 @@ Box* isinstance_func(Box* obj, Box* cls) {
} }
Box* issubclass_func(Box* child, Box* parent) { Box* issubclass_func(Box* child, Box* parent) {
if (parent->cls == classobj_cls) {
Py_FatalError("don't handle issubclass for old style classes yet");
}
RELEASE_ASSERT(child->cls == type_cls, ""); RELEASE_ASSERT(child->cls == type_cls, "");
// TODO parent can also be a tuple of classes // TODO parent can also be a tuple of classes
RELEASE_ASSERT(parent->cls == type_cls, ""); RELEASE_ASSERT(parent->cls == type_cls, "");
......
...@@ -680,6 +680,8 @@ extern "C" Box* intNew(Box* _cls, Box* val) { ...@@ -680,6 +680,8 @@ extern "C" Box* intNew(Box* _cls, Box* val) {
double d = static_cast<BoxedFloat*>(val)->d; double d = static_cast<BoxedFloat*>(val)->d;
rtn->n = d; rtn->n = d;
} else if (val->cls == bool_cls) {
rtn->n = (val == True);
} else { } else {
fprintf(stderr, "TypeError: int() argument must be a string or a number, not '%s'\n", fprintf(stderr, "TypeError: int() argument must be a string or a number, not '%s'\n",
getTypeName(val)->c_str()); getTypeName(val)->c_str());
......
...@@ -838,7 +838,7 @@ Box* strEndswith(BoxedString* self, Box* elt) { ...@@ -838,7 +838,7 @@ Box* strEndswith(BoxedString* self, Box* elt) {
return boxBool(endswith(self->s, sub->s)); return boxBool(endswith(self->s, sub->s));
} }
Box* strFind(BoxedString* self, Box* elt) { Box* strFind(BoxedString* self, Box* elt, Box* _start) {
if (self->cls != str_cls) if (self->cls != str_cls)
raiseExcHelper(TypeError, "descriptor 'find' requires a 'str' object but received a '%s'", raiseExcHelper(TypeError, "descriptor 'find' requires a 'str' object but received a '%s'",
getTypeName(elt)->c_str()); getTypeName(elt)->c_str());
...@@ -846,9 +846,21 @@ Box* strFind(BoxedString* self, Box* elt) { ...@@ -846,9 +846,21 @@ Box* strFind(BoxedString* self, Box* elt) {
if (elt->cls != str_cls) if (elt->cls != str_cls)
raiseExcHelper(TypeError, "expected a character buffer object"); raiseExcHelper(TypeError, "expected a character buffer object");
if (_start->cls != int_cls) {
raiseExcHelper(TypeError, "'start' must be an int for now");
// Real error message:
// raiseExcHelper(TypeError, "slice indices must be integers or None or have an __index__ method");
}
int64_t start = static_cast<BoxedInt*>(_start)->n;
if (start < 0) {
start += self->s.size();
start = std::max(0L, start);
}
BoxedString* sub = static_cast<BoxedString*>(elt); BoxedString* sub = static_cast<BoxedString*>(elt);
size_t r = self->s.find(sub->s); size_t r = self->s.find(sub->s, start);
if (r == std::string::npos) if (r == std::string::npos)
return boxInt(-1); return boxInt(-1);
return boxInt(r); return boxInt(r);
...@@ -1085,7 +1097,8 @@ void setupStr() { ...@@ -1085,7 +1097,8 @@ void setupStr() {
str_cls->giveAttr("startswith", new BoxedFunction(boxRTFunction((void*)strStartswith, BOXED_BOOL, 2))); str_cls->giveAttr("startswith", new BoxedFunction(boxRTFunction((void*)strStartswith, BOXED_BOOL, 2)));
str_cls->giveAttr("endswith", new BoxedFunction(boxRTFunction((void*)strEndswith, BOXED_BOOL, 2))); str_cls->giveAttr("endswith", new BoxedFunction(boxRTFunction((void*)strEndswith, BOXED_BOOL, 2)));
str_cls->giveAttr("find", new BoxedFunction(boxRTFunction((void*)strFind, BOXED_INT, 2))); str_cls->giveAttr("find",
new BoxedFunction(boxRTFunction((void*)strFind, BOXED_INT, 3, 1, false, false), { boxInt(0) }));
str_cls->giveAttr("rfind", new BoxedFunction(boxRTFunction((void*)strRfind, BOXED_INT, 2))); str_cls->giveAttr("rfind", new BoxedFunction(boxRTFunction((void*)strRfind, BOXED_INT, 2)));
str_cls->giveAttr("__add__", new BoxedFunction(boxRTFunction((void*)strAdd, UNKNOWN, 2))); str_cls->giveAttr("__add__", new BoxedFunction(boxRTFunction((void*)strAdd, UNKNOWN, 2)));
......
...@@ -26,6 +26,9 @@ class C(object): ...@@ -26,6 +26,9 @@ class C(object):
def __repr__(self): def __repr__(self):
return "<C object>" return "<C object>"
print hash(True) == hash(False)
print int(True), int(False)
c = C("hello") # This object has an invalid __nonzero__ return type c = C("hello") # This object has an invalid __nonzero__ return type
if 0: if 0:
print bool(c) # this will fail print bool(c) # this will fail
......
...@@ -69,3 +69,6 @@ for c in "aeiou": ...@@ -69,3 +69,6 @@ for c in "aeiou":
translation_map = ''.join(translation_map) translation_map = ''.join(translation_map)
print "hello world".translate(translation_map) print "hello world".translate(translation_map)
print "hello world".translate(translation_map, "") print "hello world".translate(translation_map, "")
for i in xrange(-10, 10):
print i, "aaaaa".find("a", i)
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment