Skip to content

Constructor signature matching fail. #1070

@JendaPlhak

Description

@JendaPlhak

Issue description

Hi, after release of version 2.2 I have encountered problem with binding constructor of vector.

What I would like to do is bind vector's constructor which constructs vector of n elements with given value. Instead it matches initializer list constructor and the below Python code prints 2, as it constructs vector of two elements (10, 2) instead of vector of 10 elements equal to 2.

Minimal example is following:

#include <vector>
#include <pybind11/pybind11.h>

namespace py = pybind11;

PYBIND11_MAKE_OPAQUE(std::vector<uint32_t>);

PYBIND11_MODULE(_test, m) {
    using Container = std::vector<uint32_t>;
    using T = typename Container::value_type;

    py::class_<Container, std::shared_ptr<Container>>(m, "VectorUint32")
    .def(py::init<Container::size_type, const T&>())
    .def("__len__", &Container::size);
}
from test import _test

if __name__ == '__main__':
    vec = _test.VectorUint32(10, 2)
    print(len(vec))

On Ubuntu 16.04 with gcc version 7.1.0 or 6.3 the compiler produces warning which is fine, but I still have no idea how to make it work properly.

In file included from /usr/local/include/python3.6/pybind11/pybind11.h:46:0,
                 from test.cpp:2:
/usr/local/include/python3.6/pybind11/detail/init.h: In instantiation of ‘pybind11::detail::initimpl::constructor<Args>::execute(Class&, const Extra& ...)::<lambda(pybind11::detail::value_and_holder&, Args ...)> [with Class = pybind11::class_<std::vector<unsigned int>, std::shared_ptr<std::vector<unsigned int, std::allocator<unsigned int> > > >; Extra = {}; typename std::enable_if<(! Class:: has_alias), int>::type <anonymous> = 0; Args = {long unsigned int, const unsigned int&}]’:
/usr/local/include/python3.6/pybind11/detail/init.h:163:29:   required from ‘struct pybind11::detail::initimpl::constructor<Args>::execute(Class&, const Extra& ...) [with Class = pybind11::class_<std::vector<unsigned int>, std::shared_ptr<std::vector<unsigned int, std::allocator<unsigned int> > > >; Extra = {}; typename std::enable_if<(! Class:: has_alias), int>::type <anonymous> = 0; Args = {long unsigned int, const unsigned int&}]::<lambda(struct pybind11::detail::value_and_holder&, long unsigned int, const unsigned int&)>’
/usr/local/include/python3.6/pybind11/detail/init.h:163:9:   required from ‘static void pybind11::detail::initimpl::constructor<Args>::execute(Class&, const Extra& ...) [with Class = pybind11::class_<std::vector<unsigned int>, std::shared_ptr<std::vector<unsigned int, std::allocator<unsigned int> > > >; Extra = {}; typename std::enable_if<(! Class:: has_alias), int>::type <anonymous> = 0; Args = {long unsigned int, const unsigned int&}]’
/usr/local/include/python3.6/pybind11/pybind11.h:1096:9:   required from ‘pybind11::class_<type_, options>& pybind11::class_<type_, options>::def(const pybind11::detail::initimpl::constructor<Args ...>&, const Extra& ...) [with Args = {long unsigned int, const unsigned int&}; Extra = {}; type_ = std::vector<unsigned int>; options = {std::shared_ptr<std::vector<unsigned int, std::allocator<unsigned int> > >}]’
test.cpp:13:52:   required from here
/usr/local/include/python3.6/pybind11/detail/init.h:164:31: warning: narrowing conversion of ‘std::forward<long unsigned int>(args#0)’ from ‘long unsigned int’ to ‘unsigned int’ inside { } [-Wnarrowing]
             v_h.value_ptr() = new Cpp<Class>{std::forward<Args>(args)...};
                               ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/usr/local/include/python3.6/pybind11/detail/init.h:164:31: warning: narrowing conversion of ‘std::forward<long unsigned int>(args#0)’ from ‘long unsigned int’ to ‘unsigned int’ inside { } [-Wnarrowing]```

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions