# What about an \`undefs\` function in \`Base\`?

**URL:** <https://discourse.julialang.org/t/what-about-an-undefs-function-in-base/92690>\
**Category:** General Usage\
**Tags:** feature-request\
**Created:** [January 9, 2023, 2:18am UTC](https://discourse.julialang.org/t/what-about-an-undefs-function-in-base/92690 "2023-01-09T02:18:50Z")\
**Posts on this page:** 1\
**Showing post:** 36

<div class="post-metadata">

**Author:** ![mkitti](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/mkitti/32/12459_2.png) [@mkitti](https://discourse.julialang.org/u/mkitti)\
**Post date:** [January 14, 2023, 7:28pm UTC](https://discourse.julialang.org/t/what-about-an-undefs-function-in-base/92690/36 "2023-01-14T19:28:33Z")

</div>

You are advocating a change to `Base`. If you want to make the case for it, the best way is start with a package and show that it is indispensable.

> [@alex-s-gardner](#):
>
> I’m not sure creating a new package really solves the accessibility issue that is being discussed here. A new function `undefs` is not targeted at experienced practitioners that will seek out a package to define `undefs`. The goal here is simply to further reduce barriers to entry and to new concepts, even if only a small amount. This is exactly why functions like `zeros`, `ones`, `trues`, `falses` exists.

Once upon a time, I made a [similar argument](https://github.com/JuliaLang/julia/pull/42620). We can keep discussing this, but discussing it alone will not change anything. Now I’ve created a package to move the question along. I’ve also begun registering it.

As others have mentioned, some think that `zeros`, `ones`, `trues`, and `falses` should not exist in `Base`. It places an emphasis on `Array` where perhaps it really should not be special to the user.

You have made the argument that `undefs` should be as accessible to a _novice_ user as `zeros`, `ones`, `trues`, and `falses`. However, `undefs` is dangerous. It looks like it might act like `zeros`, and more than one user on this forum has mistaken undef initialization as filling the array with `zeros`. You’ve also made the performance argument.

As Carsten Bauer mentioned, there is a better solution than `undefs` for the novice user where they can obtain nearly the same performance. This is [`calloc`](https://en.cppreference.com/w/c/memory/calloc), a standard C function. On operating systems, there also more specialized methods in the same vein. You can find my initial explorations with this here:

> [@Faster zeros with calloc](https://discourse.julialang.org/t/faster-zeros-with-calloc/69860):
>
> Abstract TL; DR zeros\_via\_calloc is a potentially faster version of zeros that is comparable to Array{T}(undef, ...) and numpy.zeros. function zeros\_via\_calloc(::Type{T}, dims::Integer...) where T ptr = Ptr{T}(Libc.calloc(prod(dims), sizeof(T))) return unsafe\_wrap(Array{T}, ptr, dims; own=true) end # Windows benchmark julia\> @btime zeros\_via\_calloc(Float64, 1024, 1024); 12.400 μs (2 allocations: 8.00 MiB) julia\> @btime zeros(Float64, 1024, 1024); 1.652 ms (2 allocations: 8.00 MiB)…

I have since packaged this into ArrayAllocators.jl. Let me offer a brief demonstration.

```julia
julia> using ArrayAllocators

julia> @time zeros(Int, 1024, 1024);
  0.011977 seconds (2 allocations: 8.000 MiB)

julia> @time Array{Int}(undef, 1024, 1024);
  0.000023 seconds (2 allocations: 8.000 MiB)

julia> @time fill!(Array{Int}(undef, 1024, 1024), 0);
  0.006183 seconds (2 allocations: 8.000 MiB)

julia> @time ArrayAllocators.zeros(Int, 1024, 1024);
  0.000175 seconds (3 allocations: 8.000 MiB)

julia> sum(ArrayAllocators.zeros(Int, 1024, 1024))
0

julia> @time Array{Int}(calloc, 1024, 1024);
  0.000026 seconds (3 allocations: 8.000 MiB)

```

Rather than making `undefs` more accessible, perhaps we should focus on making `zeros` “faster” in more cases and defer the eager usage to the `fill!` syntax.

> <https://github.com/JuliaLang/julia/issues/130>
>
> There's a clever trick that we could use to create large zero matrices really fa…st: mmap the file \`/dev/zero\`. This is, in fact, exactly what this "file" exists for. The benefit of doing this are:
> 1. It's nearly instantaneous since no memory actually needs to be allocated or filled with zeros until it's accessed.
> 2. You can read and write the memory exactly as you normally would: the kernel only allocates memory pages for you when you do something with them.
> 
> Since a fair amount of the time, no one actually touches most of the memory in a zeros array, this might be a big win. On the other hand, the drawbacks are:
> 1. Trade obvious immediate allocation cost for unobvious delayed allocation cost.
> 2. Can run out of memory on read/write instead of only on allocate.
> 3. Doesn't work for anything but \`zeros()\`, e.g. for \`ones()\`.

There’s is a minimalist philosophy attached to `Base`. As the application programming interface (API) of `Base` expands, it becomes harder to modify or change that API due to guarantees of backwards compatibility. For many, Base and standard library is already too large. A minimalist Base however is easy to customize with packages.

One reason to add new functionality to `Base` is that the functionality cannot added via a package. In particular, it may not be possible add the functionality without committing [type piracy](https://docs.julialang.org/en/v1/manual/style-guide/). Type piracy occurs when we attempt to extend methods for types where we “own” neither the method or the type. In the case of `Undefs.jl` we do not commit type piracy because we have created a new method, `undefs`. You might think that `ArrayAllocators.zeros` looks like piracy, but in fact it does not extend `Base.zeros`.

In summary, `undefs` is quite distinct from `zeros` and other methods because it can lead to novices easily writing incorrect code. Rather we should consider alternatives such as `calloc` and perhaps changing the implementation of `zeros`. These alternatives and other implementations may provide similar performance while also being correct and safe. Given the controversy the path forward is to create a package to implement the proposed functionality.

---

_[View the full topic](https://discourse.julialang.org/t/what-about-an-undefs-function-in-base/92690)._
