This commit is contained in:
blueloveTH 2023-01-27 05:52:19 +08:00
parent 5c2352fa90
commit d4401bfa98
6 changed files with 33 additions and 34 deletions

View File

@ -20,6 +20,7 @@
#include <queue>
#include <iomanip>
#include <memory>
// #include <functional>
#include <atomic>
#include <iostream>
@ -38,4 +39,8 @@
#define PK_VERSION "0.8.0"
typedef int64_t i64;
typedef double f64;
#define DUMMY_VAL (i64)0
//#define PKPY_NO_INDEX_CHECK

View File

@ -2,15 +2,13 @@
#include "safestl.h"
typedef int64_t i64;
typedef double f64;
struct CodeObject;
struct BaseRef;
class VM;
class Frame;
typedef PyVar (*_CppFunc)(VM*, const pkpy::ArgList&);
//typedef std::function<PyVar(VM*, const pkpy::ArgList&)> _CppFunc;
typedef pkpy::shared_ptr<CodeObject> _Code;
struct Function {

View File

@ -696,26 +696,23 @@ void __addModuleMath(VM* vm){
});
}
struct ReMatch {
i64 start;
i64 end;
std::smatch m;
ReMatch(i64 start, i64 end, std::smatch m) : start(start), end(end), m(m) {}
};
PyVar __regex_search(const _Str& pattern, const _Str& string, bool fromStart, VM* vm){
std::regex re(pattern);
std::smatch m;
if(std::regex_search(string, m, re)){
if(fromStart && m.position() != 0){
return vm->None;
}
PyVar ret = vm->new_object(vm->_userTypes["re.Match"], (i64)1);
vm->setattr(ret, "_start", vm->PyInt(
string.__to_u8_index(m.position())
));
vm->setattr(ret, "_end", vm->PyInt(
string.__to_u8_index(m.position() + m.length())
));
PyVarList groups(m.size());
for(size_t i = 0; i < m.size(); ++i){
groups[i] = vm->PyStr(m[i].str());
}
vm->setattr(ret, "_groups", vm->PyTuple(groups));
return ret;
if(fromStart && m.position() != 0) return vm->None;
i64 start = string.__to_u8_index(m.position());
i64 end = string.__to_u8_index(m.position() + m.length());
return vm->new_object(vm->_userTypes["re.Match"], ReMatch(start, end, m));
}
return vm->None;
};
@ -723,32 +720,29 @@ PyVar __regex_search(const _Str& pattern, const _Str& string, bool fromStart, VM
void __addModuleRe(VM* vm){
PyVar mod = vm->newModule("re");
PyVar _tp_match = vm->new_user_type_object(mod, "Match", vm->_tp_object);
vm->bindMethod("re.Match", "start", [](VM* vm, const pkpy::ArgList& args) {
vm->check_args_size(args, 1, true);
PyVar self = args[0];
return vm->getattr(self, "_start");
return vm->PyInt(UNION_GET(ReMatch, args[0]).start);
});
vm->bindMethod("re.Match", "end", [](VM* vm, const pkpy::ArgList& args) {
vm->check_args_size(args, 1, true);
PyVar self = args[0];
return vm->getattr(self, "_end");
return vm->PyInt(UNION_GET(ReMatch, args[0]).end);
});
vm->bindMethod("re.Match", "span", [](VM* vm, const pkpy::ArgList& args) {
vm->check_args_size(args, 1, true);
PyVar self = args[0];
PyVarList vec = { vm->getattr(self, "_start"), vm->getattr(self, "_end") };
auto& m = UNION_GET(ReMatch, args[0]);
PyVarList vec = { vm->PyInt(m.start), vm->PyInt(m.end) };
return vm->PyTuple(vec);
});
vm->bindMethod("re.Match", "group", [](VM* vm, const pkpy::ArgList& args) {
vm->check_args_size(args, 2, true);
auto& m = UNION_GET(ReMatch, args[0]);
int index = (int)vm->PyInt_AS_C(args[1]);
const auto& vec = vm->PyTuple_AS_C(vm->getattr(args[0], "_groups"));
vm->normalizedIndex(index, vec.size());
return vec[index];
vm->normalizedIndex(index, m.m.size());
return vm->PyStr(m.m[index].str());
});
vm->bindFunc(mod, "match", [](VM* vm, const pkpy::ArgList& args) {

View File

@ -52,11 +52,11 @@ public:
return _hash;
}
int __to_u8_index(int64_t index) const{
i64 __to_u8_index(i64 index) const{
utf8_lazy_init();
auto p = std::lower_bound(_u8_index->begin(), _u8_index->end(), index);
if(*p != index) UNREACHABLE();
return (int)(p - _u8_index->begin());
if(p != _u8_index->end() && *p != index) UNREACHABLE();
return p - _u8_index->begin();
}
int u8_length() const {

View File

@ -440,7 +440,7 @@ public:
if(it != _callable->attribs.end()){
obj = call(it->second, args, kwargs, false);
}else{
obj = new_object(_callable, (i64)-1);
obj = new_object(_callable, DUMMY_VAL);
PyVarOrNull init_fn = getattr(obj, __init__, false);
if (init_fn != nullptr) call(init_fn, args, kwargs, false);
}

View File

@ -15,3 +15,5 @@ assert re.split('测试','测试123测试12321测试') == ['', '123', '12321']
assert re.split(',','123,456,789,10') == ['123', '456', '789', '10']
assert re.split(',',',123,456,789,10') == ['', '123', '456', '789', '10']
assert re.split(',','123,456,789,10,') == ['123', '456', '789', '10']
assert re.match('1','1') is not None