Skip to content

Functions

>>> from vector import vecadd
>>> a = (5, 6, 7)
>>> b = [2]
>>> c = range(4)
>>> vecadd(a, b, c)
(7, 7, 9, 3)

Prefixed by vec... (vector).

All functions accept vectors as single exhaustible iterables.

They return vectors as tuples.

Padding is done with int(0).

The functions are type-independent. However, the data types used must support necessary scalar operations. For instance, for vector addition, coefficients must be addable — this may include operations with padded integer zeros. Empty operations return the zero vector (e.g. vecadd()==veczero) or integer zeros (e.g. vecdot(veczero, veczero)==int(0)).


Creation

veczero = ()

Zero vector.

\[ \vec{0} \qquad \mathbb{K}^0 \]

vecbasis(i, c=1)

Return the i-th basis vector times c.

\[ c\vec{e}_i \qquad \mathbb{K}^{i+1} \]

Returns a tuple with i zeros followed by c.

Source code in vector\functional.py
33
34
35
36
37
38
39
40
41
42
def vecbasis(i, c=1):
    r"""Return the `i`-th basis vector times `c`.

    $$
        c\vec{e}_i \qquad \mathbb{K}^{i+1}
    $$

    Returns a tuple with `i` zeros followed by `c`.
    """
    return (0,)*i + (c,)

vecbasisgen()

Yield all basis vectors.

\[ \left(\vec{e}_n\right)_\mathbb{n\in\mathbb{N_0}} = \left(\vec{e}_0, \vec{e}_1, \vec{e}_2, \dots \right) \]
See also
Source code in vector\functional.py
44
45
46
47
48
49
50
51
52
53
54
55
56
def vecbasisgen():
    r"""Yield all basis vectors.

    $$
        \left(\vec{e}_n\right)_\mathbb{n\in\mathbb{N_0}} = \left(\vec{e}_0, \vec{e}_1, \vec{e}_2, \dots \right)
    $$

    See also
    --------
    - for single basis vector: [`vecbasis`][vector.functional.vecbasis]
    """
    for i in count():
        yield vecbasis(i)

vecrand(n)

Return a random vector of n uniform float coefficients in [0, 1[.

\[ \vec{v}\sim\mathcal{U}^n([0, 1[) \qquad \mathbb{K}^n \]
Notes

Naming like in numpy.random, because seems more concise (not random & gauss as in the stdlib).

Source code in vector\functional.py
58
59
60
61
62
63
64
65
66
67
68
69
70
def vecrand(n):
    r"""Return a random vector of `n` uniform `float` coefficients in `[0, 1[`.

    $$
        \vec{v}\sim\mathcal{U}^n([0, 1[) \qquad \mathbb{K}^n
    $$

    Notes
    -----
    Naming like in `numpy.random`, because seems more concise
    (not `random` & `gauss` as in the stdlib).
    """
    return tuple(random() for _ in range(n))

vecrandn(n, normed=True, mu=0, sigma=1)

Return a random vector of n normal distributed float coefficients.

\[ \vec{v}\sim\mathcal{N}^n(\mu, \sigma) \qquad \mathbb{K}^n \]
Notes

Naming like in numpy.random, because seems more concise (not random & gauss as in the stdlib).

Source code in vector\functional.py
72
73
74
75
76
77
78
79
80
81
82
83
84
85
def vecrandn(n, normed=True, mu=0, sigma=1):
    r"""Return a random vector of `n` normal distributed `float` coefficients.

    $$
        \vec{v}\sim\mathcal{N}^n(\mu, \sigma) \qquad \mathbb{K}^n
    $$

    Notes
    -----
    Naming like in `numpy.random`, because seems more concise
    (not `random` & `gauss` as in the stdlib).
    """
    v = tuple(gauss(mu, sigma) for _ in range(n))
    return vectruediv(v, vecabs(v)) if normed else v

Utility

veceq(v, w)

Return if two vectors are equal.

\[ \vec{v}=\vec{w} \qquad \mathbb{K}^m\times\mathbb{K}^n\to\mathbb{B} \]
Source code in vector\functional.py
89
90
91
92
93
94
95
96
def veceq(v, w):
    r"""Return if two vectors are equal.

    $$
        \vec{v}=\vec{w} \qquad \mathbb{K}^m\times\mathbb{K}^n\to\mathbb{B}
    $$
    """
    return all(starmap(eq, zip_longest(v, w, fillvalue=0)))

vectrim(v, tol=1e-09)

Remove all trailing near zero (abs(v_i)<=tol) coefficients.

\[ \begin{pmatrix} v_0 \\ \vdots \\ v_m \end{pmatrix} \ \text{where} \ m=\max\{\, j\mid |v_{j-1}|>\text{tol}\,\}\cup\{-1\} \qquad \mathbb{K}^n\to\mathbb{K}^{\leq n} \]
Notes
  • Cutting of elements that are abs(vi)<=tol instead of abs(vi)<tol to allow cutting of elements that are exactly zero by trim(v, 0) instead of trim(v, sys.float_info.min).
  • tol=1e-9 like in PEP 485.
Source code in vector\functional.py
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
def vectrim(v, tol=1e-9):
    r"""Remove all trailing near zero (`abs(v_i)<=tol`) coefficients.

    $$
        \begin{pmatrix}
            v_0 \\
            \vdots \\
            v_m
        \end{pmatrix} \ \text{where} \ m=\max\{\, j\mid |v_{j-1}|>\text{tol}\,\}\cup\{-1\} \qquad \mathbb{K}^n\to\mathbb{K}^{\leq n}
    $$

    Notes
    -----
    - Cutting of elements that are `abs(vi)<=tol` instead of `abs(vi)<tol` to
    allow cutting of elements that are exactly zero by `trim(v, 0)` instead
    of `trim(v, sys.float_info.min)`.
    - `tol=1e-9` like in [PEP 485](https://peps.python.org/pep-0485/#defaults).
    """
    #doesn't work for iterators
    #while v and abs(v[-1])<=tol:
    #    v = v[:-1]
    #return v
    r, t = [], []
    for x in v:
        t.append(x)
        if abs(x)>tol:
            r.extend(t)
            t.clear()
    return tuple(r)

vecround(v, ndigits=None)

Round all coefficients to the given precision.

\[ (\text{round}_\text{ndigits}(v_i))_i \qquad \mathbb{K}^n\to\mathbb{K}^n \]
Source code in vector\functional.py
128
129
130
131
132
133
134
135
def vecround(v, ndigits=None):
    r"""Round all coefficients to the given precision.

    $$
        (\text{round}_\text{ndigits}(v_i))_i \qquad \mathbb{K}^n\to\mathbb{K}^n
    $$
    """
    return tuple(round(c, ndigits) for c in v)

vecrshift(v, n, fill=0)

Pad n many fills to the beginning of the vector.

\[ (v_{i-n})_i \qquad \begin{pmatrix} 0 \\ \vdots \\ 0 \\ v_0 \\ v_1 \\ \vdots \end{pmatrix} \qquad \mathbb{K}^m\to\mathbb{K}^{m+n} \]
Source code in vector\functional.py
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
def vecrshift(v, n, fill=0):
    r"""Pad `n` many `fill`s to the beginning of the vector.

    $$
        (v_{i-n})_i \qquad \begin{pmatrix}
            0 \\
            \vdots \\
            0 \\
            v_0 \\
            v_1 \\
            \vdots
        \end{pmatrix} \qquad \mathbb{K}^m\to\mathbb{K}^{m+n}
    $$
    """
    return tuple(chain((fill,)*n, v))

veclshift(v, n)

Remove n many coefficients at the beginning of the vector.

\[ (v_{i+n})_i \qquad \begin{pmatrix} v_n \\ v_{n+1} \\ \vdots \end{pmatrix} \qquad \mathbb{K}^m\to\mathbb{K}^{\max\{m-n, 0\}} \]
Source code in vector\functional.py
153
154
155
156
157
158
159
160
161
162
163
164
def veclshift(v, n):
    r"""Remove `n` many coefficients at the beginning of the vector.

    $$
        (v_{i+n})_i \qquad \begin{pmatrix}
            v_n \\
            v_{n+1} \\
            \vdots
        \end{pmatrix} \qquad \mathbb{K}^m\to\mathbb{K}^{\max\{m-n, 0\}}
    $$
    """
    return tuple(islice(v, n, None))

Hilbert space

vecabsq(v)

Return the sum of absolute squares of the coefficients.

\[ ||\vec{v}||_{\ell_{\mathbb{N}_0}^2}^2=\sum_i|v_i|^2 \qquad \mathbb{K}^n\to\mathbb{K}_0^+ \]
Notes

Reasons why it exists:

  • Occurs in math.
  • Most importantly: type independent because it doesn't use sqrt.
References
Source code in vector\functional.py
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
def vecabsq(v):
    r"""Return the sum of absolute squares of the coefficients.

    $$
        ||\vec{v}||_{\ell_{\mathbb{N}_0}^2}^2=\sum_i|v_i|^2 \qquad \mathbb{K}^n\to\mathbb{K}_0^+
    $$

    Notes
    -----
    Reasons why it exists:

    - Occurs in math.
    - Most importantly: type independent because it doesn't use `sqrt`.

    References
    ----------
    - <https://docs.python.org/3/library/itertools.html#itertools-recipes>: `sum_of_squares`
    """
    #return sumprod(v, v) #no abs
    return sumprod(*tee(map(abs, v), 2))

vecabs(v)

Return the Euclidean/L2-norm.

\[ ||\vec{v}||_{\ell_{\mathbb{N}_0}^2}=\sqrt{\sum_i|v_i|^2} \qquad \mathbb{K}^n\to\mathbb{K}_0^+ \]

Returns the square root of vecabsq.

Source code in vector\functional.py
189
190
191
192
193
194
195
196
197
198
199
200
201
def vecabs(v):
    r"""Return the Euclidean/L2-norm.

    $$
        ||\vec{v}||_{\ell_{\mathbb{N}_0}^2}=\sqrt{\sum_i|v_i|^2} \qquad \mathbb{K}^n\to\mathbb{K}_0^+
    $$

    Returns the square root of [`vecabsq`][vector.functional.vecabsq].
    """
    #hypot(*v) doesn't work for complex
    #math.sqrt doesn't work for complex and cmath.sqrt always returns complex
    #therefore use **0.5 instead of sqrt because it is type conserving
    return vecabsq(v)**0.5

vecdot(v, w)

Return the inner product of two vectors without conjugation.

\[ \left<\vec{v}\mid\vec{w}\right>_{\ell_{\mathbb{N}_0}^2}=\sum_iv_iw_i \qquad \mathbb{K}^m\times\mathbb{K}^n\to\mathbb{K} \]
Source code in vector\functional.py
203
204
205
206
207
208
209
210
211
212
213
def vecdot(v, w):
    r"""Return the inner product of two vectors without conjugation.

    $$
        \left<\vec{v}\mid\vec{w}\right>_{\ell_{\mathbb{N}_0}^2}=\sum_iv_iw_i \qquad \mathbb{K}^m\times\mathbb{K}^n\to\mathbb{K}
    $$
    """
    #unreadable and doesn't work for generators
    #return sumprod(v[:min(len(v), len(w))], w[:min(len(v), len(w))])
    #return sumprod(*zip(*zip(v, w))) #would be more precise, but is bloat
    return sum(map(mul, v, w))

vecparallel(v, w)

Return if two vectors are parallel.

\[ \vec{v}\parallel\vec{w} \qquad ||\vec{v}||\,||\vec{w}|| \overset{?}{=} |\vec{v}\vec{w}|^2 \qquad \mathbb{K}^m\times\mathbb{K}^n\to\mathbb{B} \]
Source code in vector\functional.py
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
def vecparallel(v, w):
    r"""Return if two vectors are parallel.

    $$
        \vec{v}\parallel\vec{w} \qquad ||\vec{v}||\,||\vec{w}|| \overset{?}{=} |\vec{v}\vec{w}|^2 \qquad \mathbb{K}^m\times\mathbb{K}^n\to\mathbb{B}
    $$
    """
    #doesn't work for exhaustible iterables
    #return vecabsq(v)*vecabsq(w) == abs(vecdot(v, w))**2
    v2, w2, vw = 0, 0, 0
    for vi, wi in zip_longest(v, w, fillvalue=0):
        via, wia = abs(vi), abs(wi)
        v2 += via * via
        w2 += wia * wia
        vw += vi * wi
    vw = abs(vw)
    return v2 * w2 == vw * vw

Vector space

vecpos(v)

Return the vector with the unary positive operator applied.

\[ +\vec{v} \qquad \mathbb{K}^n\to\mathbb{K}^n \]
Source code in vector\functional.py
235
236
237
238
239
240
241
242
def vecpos(v):
    r"""Return the vector with the unary positive operator applied.

    $$
        +\vec{v} \qquad \mathbb{K}^n\to\mathbb{K}^n
    $$
    """
    return tuple(map(pos, v))

vecneg(v)

Return the vector with the unary negative operator applied.

\[ -\vec{v} \qquad \mathbb{K}^n\to\mathbb{K}^n \]
Source code in vector\functional.py
244
245
246
247
248
249
250
251
def vecneg(v):
    r"""Return the vector with the unary negative operator applied.

    $$
        -\vec{v} \qquad \mathbb{K}^n\to\mathbb{K}^n
    $$
    """
    return tuple(map(neg, v))

vecadd(*vs)

Return the sum of vectors.

\[ \vec{v}_0+\vec{v}_1+\cdots \qquad \mathbb{K}^{n_0}\times\mathbb{K}^{n_1}\times\cdots\to\mathbb{K}^{\max_i n_i} \]
Source code in vector\functional.py
253
254
255
256
257
258
259
260
def vecadd(*vs):
    r"""Return the sum of vectors.

    $$
        \vec{v}_0+\vec{v}_1+\cdots \qquad \mathbb{K}^{n_0}\times\mathbb{K}^{n_1}\times\cdots\to\mathbb{K}^{\max_i n_i}
    $$
    """
    return tuple(map(sum, zip_longest(*vs, fillvalue=0)))

vecaddc(v, c, i=0)

Return v with c added to the i-th coefficient.

\[ \vec{v}+c\vec{e}_i \qquad \mathbb{K}^n\to\mathbb{K}^{\max\{n, i\}} \]

More efficient than vecadd(v, vecbasis(i, c)).

Source code in vector\functional.py
262
263
264
265
266
267
268
269
270
271
272
273
274
def vecaddc(v, c, i=0):
    r"""Return `v` with `c` added to the `i`-th coefficient.

    $$
        \vec{v}+c\vec{e}_i \qquad \mathbb{K}^n\to\mathbb{K}^{\max\{n, i\}}
    $$

    More efficient than `vecadd(v, vecbasis(i, c))`.
    """
    v = list(v)
    v.extend([0] * (i-len(v)+1))
    v[i] += c
    return tuple(v)

vecsub(v, w)

Return the difference of two vectors.

\[ \vec{v}-\vec{w} \qquad \mathbb{K}^m\times\mathbb{K}^n\to\mathbb{K}^{\max\{m, n\}} \]
Source code in vector\functional.py
276
277
278
279
280
281
282
283
def vecsub(v, w):
    r"""Return the difference of two vectors.

    $$
        \vec{v}-\vec{w} \qquad \mathbb{K}^m\times\mathbb{K}^n\to\mathbb{K}^{\max\{m, n\}}
    $$
    """
    return tuple(starmap(sub, zip_longest(v, w, fillvalue=0)))

vecmul(a, v)

Return the product of a scalar and a vector.

\[ a\vec{v} \qquad \mathbb{K}\times\mathbb{K}^n\to\mathbb{K}^n \]
Source code in vector\functional.py
285
286
287
288
289
290
291
292
def vecmul(a, v):
    r"""Return the product of a scalar and a vector.

    $$
        a\vec{v} \qquad \mathbb{K}\times\mathbb{K}^n\to\mathbb{K}^n
    $$
    """
    return tuple(map(mul, repeat(a), v))

vectruediv(v, a)

Return the true division of a vector and a scalar.

\[ \frac{\vec{v}}{a} \qquad \mathbb{K}^n\times\mathbb{K}\to\mathbb{K}^n \]
Notes

Why called truediv instead of div?

  • div would be more appropriate for an absolute clean mathematical implementation, that doesn't care about the language used. But the package might be used for pure integers/integer arithmetic, so both, truediv and floordiv operations have to be provided, and none should be privileged over the other by getting the universal div name.
  • truediv/floordiv is unambiguous, like Python operators.
Source code in vector\functional.py
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
def vectruediv(v, a):
    r"""Return the true division of a vector and a scalar.

    $$
        \frac{\vec{v}}{a} \qquad \mathbb{K}^n\times\mathbb{K}\to\mathbb{K}^n
    $$

    Notes
    -----
    Why called `truediv` instead of `div`?

    - `div` would be more appropriate for an absolute clean mathematical
    implementation, that doesn't care about the language used. But the package
    might be used for pure integers/integer arithmetic, so both, `truediv`
    and `floordiv` operations have to be provided, and none should be
    privileged over the other by getting the universal `div` name.
    - `truediv`/`floordiv` is unambiguous, like Python `operator`s.
    """
    return tuple(map(truediv, v, repeat(a)))

vecfloordiv(v, a)

Return the floor division of a vector and a scalar.

\[ \left(\left\lfloor\frac{v_i}{a}\right\rfloor\right)_i \qquad \mathbb{K}^n\times\mathbb{K}\to\mathbb{K}^n \]
Source code in vector\functional.py
314
315
316
317
318
319
320
321
def vecfloordiv(v, a):
    r"""Return the floor division of a vector and a scalar.

    $$
        \left(\left\lfloor\frac{v_i}{a}\right\rfloor\right)_i \qquad \mathbb{K}^n\times\mathbb{K}\to\mathbb{K}^n
    $$
    """
    return tuple(map(floordiv, v, repeat(a)))

vecmod(v, a)

Return the elementwise mod of a vector and a scalar.

\[ \left(v_i \mod a\right)_i \qquad \mathbb{K}^n\times\mathbb{K}\to\mathbb{K}^n \]
Source code in vector\functional.py
323
324
325
326
327
328
329
330
def vecmod(v, a):
    r"""Return the elementwise mod of a vector and a scalar.

    $$
        \left(v_i \mod a\right)_i \qquad \mathbb{K}^n\times\mathbb{K}\to\mathbb{K}^n
    $$
    """
    return tuple(map(mod, v, repeat(a)))

vecdivmod(v, a)

Return the elementwise divmod of a vector and a scalar.

\[ \left(\left\lfloor\frac{v_i}{a}\right\rfloor\right)_i, \ \left(v_i \mod a\right)_i \qquad \mathbb{K}^n\times\mathbb{K}\to\mathbb{K}^n\times\mathbb{K}^n \]
Source code in vector\functional.py
332
333
334
335
336
337
338
339
340
341
342
343
344
def vecdivmod(v, a):
    r"""Return the elementwise divmod of a vector and a scalar.

    $$
        \left(\left\lfloor\frac{v_i}{a}\right\rfloor\right)_i, \ \left(v_i \mod a\right)_i \qquad \mathbb{K}^n\times\mathbb{K}\to\mathbb{K}^n\times\mathbb{K}^n
    $$
    """
    q, r = [], []
    for vi in v:
        qi, ri = divmod(vi, a)
        q.append(qi)
        r.append(ri)
    return tuple(q), tuple(r)

Elementwise

vechadamard(*vs)

Return the elementwise product of vectors.

\[ \left((\vec{v}_0)_i\cdot(\vec{v}_1)_i\cdot\cdots\right)_i \qquad \mathbb{K}^{n_0}\times\mathbb{K}^{n_1}\times\cdots\to\mathbb{K}^{\min_i n_i} \]
Source code in vector\functional.py
348
349
350
351
352
353
354
355
def vechadamard(*vs):
    r"""Return the elementwise product of vectors.

    $$
        \left((\vec{v}_0)_i\cdot(\vec{v}_1)_i\cdot\cdots\right)_i \qquad \mathbb{K}^{n_0}\times\mathbb{K}^{n_1}\times\cdots\to\mathbb{K}^{\min_i n_i}
    $$
    """
    return tuple(map(prod, zip(*vs)))

vechadamardtruediv(v, w)

Return the elementwise true division of two vectors.

\[ \left(\frac{v_i}{w_i}\right)_i \qquad \mathbb{K}^m\times\mathbb{K}^n\to\mathbb{K}^m \]
Source code in vector\functional.py
357
358
359
360
361
362
363
364
def vechadamardtruediv(v, w):
    r"""Return the elementwise true division of two vectors.

    $$
        \left(\frac{v_i}{w_i}\right)_i \qquad \mathbb{K}^m\times\mathbb{K}^n\to\mathbb{K}^m
    $$
    """
    return tuple(map(truediv, v, chain(w, repeat(0))))

vechadamardfloordiv(v, w)

Return the elementwise floor division of two vectors.

\[ \left(\left\lfloor\frac{v_i}{w_i}\right\rfloor\right)_i \qquad \mathbb{K}^m\times\mathbb{K}^n\to\mathbb{K}^m \]
Source code in vector\functional.py
366
367
368
369
370
371
372
373
def vechadamardfloordiv(v, w):
    r"""Return the elementwise floor division of two vectors.

    $$
        \left(\left\lfloor\frac{v_i}{w_i}\right\rfloor\right)_i \qquad \mathbb{K}^m\times\mathbb{K}^n\to\mathbb{K}^m
    $$
    """
    return tuple(map(floordiv, v, chain(w, repeat(0))))

vechadamardmod(v, w)

Return the elementwise mod of two vectors.

\[ \left(v_i \mod w_i\right)_i \qquad \mathbb{K}^m\times\mathbb{K}^n\to\mathbb{K}^m \]
Source code in vector\functional.py
375
376
377
378
379
380
381
382
def vechadamardmod(v, w):
    r"""Return the elementwise mod of two vectors.

    $$
        \left(v_i \mod w_i\right)_i \qquad \mathbb{K}^m\times\mathbb{K}^n\to\mathbb{K}^m
    $$
    """
    return tuple(map(mod, v, chain(w, repeat(0))))

vechadamardmin(*vs)

Return the elementwise minimum of vectors.

\[ \left(\min((\vec{v}_0)_i,(\vec{v}_1)_i,\cdots)\right)_i \qquad \mathbb{K}^{n_0}\times\mathbb{K}^{n_1}\times\cdots\to\mathbb{K}^{\max_i n_i} \]
Source code in vector\functional.py
384
385
386
387
388
389
390
391
def vechadamardmin(*vs):
    r"""Return the elementwise minimum of vectors.

    $$
        \left(\min((\vec{v}_0)_i,(\vec{v}_1)_i,\cdots)\right)_i \qquad \mathbb{K}^{n_0}\times\mathbb{K}^{n_1}\times\cdots\to\mathbb{K}^{\max_i n_i}
    $$
    """
    return tuple(map(min, zip_longest(*vs, fillvalue=inf)))

vechadamardmax(*vs)

Return the elementwise maximum of vectors.

\[ \left(\max((\vec{v}_0)_i,(\vec{v}_1)_i,\cdots)\right)_i \qquad \mathbb{K}^{n_0}\times\mathbb{K}^{n_1}\times\cdots\to\mathbb{K}^{\max_i n_i} \]
Source code in vector\functional.py
393
394
395
396
397
398
399
400
def vechadamardmax(*vs):
    r"""Return the elementwise maximum of vectors.

    $$
        \left(\max((\vec{v}_0)_i,(\vec{v}_1)_i,\cdots)\right)_i \qquad \mathbb{K}^{n_0}\times\mathbb{K}^{n_1}\times\cdots\to\mathbb{K}^{\max_i n_i}
    $$
    """
    return tuple(map(max, zip_longest(*vs, fillvalue=-inf)))