# Vector Math (VM) Classes

## Introduction

The VM library provides methods to operate on vectors of float or integer data. The library will use SIMD instructions (Altivec, SSE, etc.) so operations may be more efficient than native code.

Most functions have several different signatures for uniform or varying values. A uniform value is the same for all elements of the vector arrays (i.e. a scalar value). A varying value is potentially different.

For example

```    void
function(fpreal32 *a, fpreal32 *b, int nfloats)
{
// Use the mul operation to multiply a by a scalar/uniform value
VM_Math::mul(a, a, 1.3);

// Now, use the varying function to multiply by a vector/varying value
VM_Math::mul(a, a, b);
}
```

Most functions also have a SISD implementation which is illustrative of what the function actually does. The vector forms can be significantly faster than the SISD versions.

For example, to add one array of floats to another, instead of

```    void
addFloats(float *a, const float *b, int nfloats)
{
int             i;
for (i = 0; i < nfloats; i++)
a[i] += b[i];
}
```
you could use (which is often faster).
```    void
addFloats(float *a, const float *b, int nfloats)
{
}
```

## Comparison functions

There are two forms of comparison functions. The fast version of the standard operations (i.e. VM_Math::lt()) will return 0 or 1 only. The fast version (i.e. VM_Math::fastlt()) will return 0 for `false` values, but may return any other value for `true` values.

• ` VM_Math::lt(d, a, b) `
d[i] = a[i] < b[i]
• ` VM_Math::fastlt(d, a, b) `
d[i] = a[i] < b
• ` VM_Math::le(d, a, b) `
d[i] = a[i] <= b[i]
• ` VM_Math::fastle(d, a, b) `
d[i] = a[i] <= b
• ` VM_Math::gt(d, a, b) `
d[i] = a[i] > b[i]
• ` VM_Math::fastgt(d, a, b) `
d[i] = a[i] > b
• ` VM_Math::ge(d, a, b) `
d[i] = a[i] >= b[i]
• ` VM_Math::fastge(d, a, b) `
d[i] = a[i] >= b
• ` VM_Math::eq(d, a, b) `
d[i] = a[i] == b[i]
• ` VM_Math::fasteq(d, a, b) `
d[i] = a[i] == b
• ` VM_Math::ne(d, a, b) `
d[i] = a[i] != b[i]
• ` VM_Math::fastne(d, a, b) `
d[i] = a[i] != b

## Basic arithmetic

• ` VM_Math::add(d, a, b) `
d[i] = a[i] + b[i]
• ` VM_Math::sub(d, a, b) `
d[i] = a[i] - b[i]
• ` VM_Math::mul(d, a, b) `
d[i] = a[i] * b[i]
• ` VM_Math::div(d, a, b) `
d[i] = a[i] / b[i]
• ` VM_Math::safediv(d, a, b) `
d[i] = b[i] != 0 ? a[i] / b[i] : a[i]
• ` VM_Math::fdiv(d, a, b) `
d[i] = a[i] * (1.0 / b[i])
Faster than div() since it uses the reciprocal function
• ` VM_Math::max(d, a, b) `
d[i] = SYSmax(a[i], b[i])
• ` VM_Math::min(d, a, b) `
d[i] = SYSmin(a[i], b[i])
• ` VM_Math::clamp(d, a, b) `
d[i] = SYSclamp(a[i], min, max)
• ` VM_Math::dot(a,b,n) `
return sum(a[i]*b[i], i=0,n)
• ` VM_Math::zerocount(a,n) `
return sum(a[i]==0, i=0,n)
• ` VM_Math::scaleoffset(d, a, b)`
d[i] = d[i]*a[i] + b[i]
• ` VM_Math::madd(d, a, b) `
d[i] = d[i] + a[i]*b[i]
• ` VM_Math::sqrt(d, a) `
d[i] = sqrt(a[i])
• ` VM_Math::fsqrt(d, a) `
d[i] = 1.0 / isqrt(a[i])
Faster, but less accurate version of `sqrt()` since it uses the reciprocal function.
• ` VM_Math::isqrt(d, a) `
d[i] = 1.0 / sqrt(a[i])
• ` VM_Math::floor(a) `
SYSfloor(a)
• ` VM_Math::cast(a) `
(int)a
• ` VM_Math::negate(d, a) `
d[i] = -a[i]
• ` VM_Math::invert(d, a) `
d[i] = 1.0 / a[i]
• ` VM_Math::abs(d, a) `
d[i] = abs(a[i])
• ` VM_Math::wpoint(d,a,b,c,e) `
d[i] = SYSclamp(a[i]*b+e+0.5F, 0, c)
• ` VM_Math::iwpoint(d,a,b,e) `
d[i] = (fpreal32)(a[i]-e)/b;
• ` VM_Math::set(d, a) `
d[i] = a
• ` VM_Math::set(d, a, disabled)`
d[i] = disabled[i] ? d[i] : a[i]
• ` VM_Math::lerp(d, a, b, t) `
d[i] = a[i] + (b[i]-a[i])*t[i]

Generated on Thu Jan 31 00:29:27 2013 for HDK by  1.5.9