It depends on what you mean. If the question is about plain arrays, meaning a sequence of contiguos memory locations and for initialization you mean putting a value in every memory location of this "matrix" then the answer is no, better than O(n*m) is not possible and we can prove it:
Let us assume that algorithm fill(A[n][m], init_val)
is correct(i.e. fills all the memory locations of A
) has complexity g(n,m)
which is less than O(n*m)
(meaning g(n,m)
is not part of Ω(n*m)
), then for big enough n
and m
we will have that g(n,m) < n*m
= number of memory locations. Since filling a memory location requires one operation the algorithm fill
can fill at most g(n,m)
locations[actually half because it must also do at least an operation to "select" a different memory location, except if the hardware provides a combined operation] which is strictly less than n*m
, which imply that the algorithm fill
is not correct.
The same applies if filling k
memory locations takes constant time, you simply have to choose bigger n
and m
values.
As other already suggested you can use other data-structures to avoid the O(n^2)
initialization time. amit suggestion uses some kind of lazy-evaluation, which allows you to not initialize the array at all but do it only when you access the elements.
Note that this removes the Ω(n^2)
cost at the beginning, but requires more complex operations to access the array's elements and also requires more memory.
It is not clear what your interviewer meant: converting an array into a linked-list requires Ω(L)
time(where L is the length of the array), so simply converting the whole matrix into a linked-list would require Ω(n^2)
time plus the real initialization. Using recursion does not help at all,
you simply end up in recurrences such as T(n) = 2T(n/2) + O(1)
which would again result in no benefit for the asymptotic complexity.
As a general rule all algorithms have to scan at least all of their input, except it they have some form of knowledge beforehand(e.g. elements are sorted). In your case the space to scan is Θ(n^2)
and thus every algorithm that wants to fill it must be at least Ω(n^2)
. Anything with less than this complexity either make some assumption(e.g. the memory contains the initializer value by default -> O(1)
), or solves a different problem(e.g. use lazy arrays, or other data structures).