Commit fa70f079 authored by Georges Racinet's avatar Georges Racinet
Browse files

Starting point

At this stage, we have a very minimal working Rust implementation for
sets of integers in Rust, and we don't try and provide multiple references
to it to the Python side.
parents
^target/
glob:*.rs.bk
glob:Cargo.lock
syntax: glob
__pycache__/
*.pyc
*~
\#*\#
.\#*
[package]
name = "py_shared_ref"
version = "0.1.0"
authors = ["Georges Racinet <georges.racinet@octobus.net>"]
[lib]
crate-type = ["cdylib"]
[dependencies]
cpython = '*'
[features]
default = ["python3"]
python27 = ["cpython/python27-sys", "cpython/extension-module-2-7"]
python3 = ["cpython/python3-sys", "cpython/extension-module"]
\ No newline at end of file
#!/usr/bin/env python3
import sys
if sys.version_info.major < 3:
sys.stderr.write("Please run with Python 3\n")
sys.exit(1)
if __name__ == '__main__':
from tests import run
run()
//! This crate demonstrates how to provide shared references to the
//! Python side.
//!
//! # Problem statement
//! Imagine you need to own some datastructure, expose it directly to Python
//! and at the same time expose some reference to it in another Python object.
//!
//! The typical case would be to implement some collection and provide
//! Python iterators over it.
extern crate cpython;
use cpython::*;
use std::cell::RefCell;
use std::collections::HashSet;
type Inner = HashSet<u32>;
py_class!(class RustSet |py| {
data hs: RefCell<Inner>;
def __new__(_cls) -> PyResult<RustSet> {
Self::create_instance(py, RefCell::new(Inner::new()))
}
def __contains__(&self, v: u32) -> PyResult<bool> {
Ok(self.hs(py).borrow().contains(&v))
}
def add(&self, v: u32) -> PyResult<PyObject> {
self.hs(py).borrow_mut().insert(v);
Ok(py.None())
}
def extend(&self, iterable: &PyObject) -> PyResult<PyObject> {
let mut hs = self.hs(py).borrow_mut();
for vobj in iterable.iter(py)? {
hs.insert(vobj?.extract::<u32>(py)?);
}
Ok(py.None())
}
});
py_module_initializer!(shared_ref, initshared_ref, PyInit_shared_ref, |py, m| {
m.add(
py,
"__doc__",
"Demonstrator of shared Rust references within Python",
)?;
m.add_class::<RustSet>(py)?;
Ok(())
});
try:
from .shared_ref import RustSet
except ImportError:
import sys
sys.stderr.write("Rust extension not found. Please run 'cargo build' "
"first (without '--release')\n")
sys.exit(1)
def test_basic():
"""Test basic scaffolding API: not needing to share refs."""
rs = RustSet()
rs.add(3)
assert 3 in rs
assert 4 not in rs
rs.extend(x**2 for x in range(10))
assert 4 in rs
assert 81 in rs
assert 65 not in rs
def run():
test_basic()
../target/debug/libpy_shared_ref.so
\ No newline at end of file
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