Skip to content

ctypes.Array should be abstract #6349

Closed

Description

@sobolevn

Right now Array in ctypes is a regular class:

class Array(Generic[_CT], _CData):
_length_: ClassVar[int]

But, in reallity - you cannot instantiate it:

>>> from ctypes import Array, c_int
>>> i = c_int(1)
>>> Array(i)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: abstract class

Mypy is also not happy with Array(...) but for other reasons:

out/ex.py:4: error: Array constructor argument 1 of type "c_int" is not convertible to the array element type <nothing>
out/ex.py:4: note: Revealed type is "ctypes.Array[<nothing>]"

Array(...) is not tested in https://github.com/python/mypy/blob/master/test-data/unit/check-ctypes.test at all

Activity

  1. JelleZijlstra commented on Nov 20, 2021

    @JelleZijlstra
    Member

    Note that mypy has a dedicated plugin for ctypes (https://github.com/python/mypy/blob/master/mypy/plugins/ctypes.py), so not everything here may be fixable in typeshed.

  2. added
    reason: inexpressibleClosed, because this can't be expressed within the current type system
    on Nov 22, 2021
  3. srittau commented on Nov 22, 2021

    @srittau
    Collaborator

    I don't think there is a good way to make Array abstract in typeshed. As it doesn't derive from abc.ABCMeta at runtime, we shouldn't derive it either. If you have an idea on how to mark it, please open a PR. Until then I'm closing this as "inexpressable".

  4. sobolevn commented on Nov 22, 2021

    @sobolevn
    MemberAuthor

    We can try to make _length_ and _type_ abstract properties: https://github.com/python/cpython/blob/main/Modules/_ctypes/_ctypes.c#L1522-L1526

    Docs: https://github.com/python/cpython/blob/1cbaa505d007e11c4a1f0d2073d72b6c02c7147c/Doc/library/ctypes.rst#arrays-and-pointers

    This way, we would have a class with "abtract" attributes and it won't be possible to create instances of it.
    It would be also helpful for subclassing like

    class X(object, Array):
       _length_ = 5
       _type_ = "i"
  5. sobolevn commented on Nov 22, 2021

    @sobolevn
    MemberAuthor

    But, they should be writable:

    >>> from ctypes import c_int
    >>> x = c_int * 3
    >>> x
    <class '__main__.c_int_Array_3'>
    >>> x._length_
    3
    >>> x._length_ = 2
    >>> x._type_ = 'a'
  6. sobolevn commented on Nov 23, 2021

    @sobolevn
    MemberAuthor

    Refs #6348

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    reason: inexpressibleClosed, because this can't be expressed within the current type system

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions