Skip to content

No type error when deleting from an array an invalid type #988

Open

Description

@refi64

Example:

ar = [] of Int32
ar.delete "abc"

This has caused bugs for me before.

Activity

  1. refi64 commented on Jul 16, 2015

    @refi64
    ContributorAuthor

    Real-life example:

    Consider these two functions:

          # Mark a register as no longer used.
          def freereg(reg)
            @usedregs.delete reg
          end
    
          # Free a register if it's a register item.
          def ofree(maybereg)
            self.freereg maybereg.reg if maybereg.is_a? Parser::RegItem
          end

    I had originally written the second-to-last line as:

    self.freereg maybereg if maybereg.is_a? Parser::RegItem

    @usedregs is supposed to be of the type Register, which is completely independent from Parser::RegItem. Because I was passing the wrong type to freereg, the register was never freed. This caused that to lurk as a bug until my compiler crashed because it ran out of registers.

  2. refi64 commented on Jul 16, 2015

    @refi64
    ContributorAuthor

    Possible fix: change line 418 of array.cr to:

    def delete(obj : T)
  3. asterite commented on Jul 16, 2015

    @asterite
    Member

    This is interesting :-)

    In Java for example removing an element is not restricted to a type. This is because you delete elements by equality. So, this works in Ruby (and in Crystal):

    a = [1, 2, 3]
    a.delete 1.0
    a #=> [2, 3]

    So I'm not sure what we should do here. This is an excellent opportunity to discuss it :-)

  4. refi64 commented on Jul 16, 2015

    @refi64
    ContributorAuthor

    @asterite Well, Ruby is duck-typed, and Java is pretty stupid. ;)

    I'm just saying this because I don't think anyone has ever done that intentionally, as it doesn't really serve a purpose. What would the point of it be? a could never hold floats, anyway.

    Just my three cents. :)

  5. vendethiel commented on Jul 16, 2015

    @vendethiel
    Contributor

    I think I side with @kirbyfan64 here, for the sole purpose of catching type errors earlier

  6. asterite commented on Jul 18, 2015

    @asterite
    Member

    I think it makes sense to put a type restriction there. The same happens with Hash#[], which doesn't have a restriction but maybe it should.

  7. straight-shoota commented on Dec 7, 2020

    @straight-shoota
    Member

    For hash there's #8893

  8. nobodywasishere commented on Jan 27, 2025

    @nobodywasishere
    Contributor

    This (and hash-key types) could be added as checks for a linter if it's desired to not break stdlib. I'm currently working on adding the ability to have semantic rules like this to ameba.

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

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions