Skip to content

Commit

Permalink
add trigonometric (and a few other) functions
Browse files Browse the repository at this point in the history
  • Loading branch information
dastrobu committed Dec 23, 2021
1 parent 04cf174 commit 734e778
Show file tree
Hide file tree
Showing 5 changed files with 1,407 additions and 3 deletions.
69 changes: 66 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ simple handling of multidimensional data.

<!-- START doctoc generated TOC please keep comment here to allow auto update -->
<!-- DON'T EDIT THIS SECTION, INSTEAD RE-RUN doctoc TO UPDATE -->
(generated with [DocToc](https://github.com/thlorenz/doctoc))

- [Installation](#installation)
- [Swift Package Manager](#swift-package-manager)
Expand All @@ -38,6 +37,7 @@ simple handling of multidimensional data.
- [Numerical Backend](#numerical-backend)
- [Not Implemented](#not-implemented)
- [Out of Scope](#out-of-scope)
- [Docs](#docs)

<!-- END doctoc generated TOC please keep comment here to allow auto update -->

Expand Down Expand Up @@ -272,7 +272,71 @@ print(a.reshaped([2, 2, 3]))

A copy will only be made if required to create an array with the specified order.

## Linear Algebra Operations for `Double` and `Float` NdArrays.
## Elementwise Operations

### Scalars

Arithmetic operations with scalars work in-place,

```swift
let a = NdArray<Double>.ones([2, 2])
a *= 2
a /= 2
a += 2
a /= 2
```

or with implicit copies.

```swift
var b: NdArray<Double>
b = a * 2
b = a / 2
b = a + 2
b = a - 2
```

### Basic Functions

The following basic functions can be applied to any `Float` or `Double` array.

```swift
let a = NdArray<Double>.ones([2, 2])
var b: NdArray<Double>

b = abs(a)

b = acos(a)
b = asin(a)
b = atan(a)

b = cos(a)
b = sin(a)
b = tan(a)

b = cosh(a)
b = sinh(a)
b = tanh(a)

b = exp(a)
b = exp2(a)

b = log(a)
b = log10(a)
b = log1p(a)
b = log2(a)
b = logb(a)
```

The `abs` function is also defined for `SignedNumeric`, such as `Int` arrays.

```swift
let a = NdArray<Int>.range(from: -2, to: 2)
print(a) // [-2, -1, 0, 1]
print(abs(a)) // [2, 1, 0, 1]
```

## Linear Algebra Operations for `Double` and `Float` `NdArray`s.

Linear algebra support is currently very basic.

Expand Down Expand Up @@ -424,7 +488,6 @@ The functions of these libraries are provided by the

Some features are not implemented yet, but are planned for the near future.

* Trigonometric functions
* Elementwise multiplication of Double and Float arrays. Planned as `multiply(elementwiseBy, divide(elementwiseBy)`
employing `vDSP_vmulD`
Note that this can be done with help of `map` currently.
Expand Down
228 changes: 228 additions & 0 deletions Sources/NdArray/basic_functions.swift
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
//

import Accelerate
import Darwin

// SignedNumeric and Comparable

Expand All @@ -14,6 +15,7 @@ public func abs<K: SignedNumeric, T: NdArray<K>>(_ a: T) -> T where K: Comparabl

// Double

/// see ``vDSP_vabsD``.
public func abs<T: NdArray<Double>>(_ a: T, out b: T) {
a.apply1d(other: b, f1d: { _ in
vDSP_vabsD(a.data, a.strides[0], b.data, b.strides[0], vDSP_Length(a.shape[0]))
Expand All @@ -30,8 +32,122 @@ public func abs<T: NdArray<Double>>(_ a: T) -> T {
return b
}

/// see ``Darwin/asin``.
public func asin<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.asin)
return b
}

/// see ``Darwin/acos``.
public func acos<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.acos)
return b
}

/// see ``Darwin/atan``.
public func atan<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.atan)
return b
}

/// see ``Darwin/cos``.
public func cos<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.cos)
return b
}

/// see ``Darwin/sin``.
public func sin<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.sin)
return b
}

/// see ``Darwin/tan``.
public func tan<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.tan)
return b
}

/// see ``Darwin/cosh``.
public func cosh<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.cosh)
return b
}

/// see ``Darwin/sinh``.
public func sinh<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.sinh)
return b
}

/// see ``Darwin/tanh``.
public func tanh<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.tanh)
return b
}

/// see ``Darwin/exp``.
public func exp<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.exp)
return b
}

/// see ``Darwin/exp2``.
public func exp2<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.exp2)
return b
}

/// see ``Darwin/log``.
public func log<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.log)
return b
}

/// see ``Darwin/log10``.
public func log10<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.log10)
return b
}

/// see ``Darwin/log1p``.
public func log1p<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.log1p)
return b
}

/// see ``Darwin/log2``.
public func log2<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.log2)
return b
}

/// see ``Darwin/logb``.
public func logb<T: NdArray<Double>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.logb)
return b
}

// Float


/// see ``vDSP_vabsD``.
public func abs<T: NdArray<Float>>(_ a: T, out b: T) {
a.apply1d(other: b, f1d: { _ in
vDSP_vabs(a.data, a.strides[0], b.data, b.strides[0], vDSP_Length(a.shape[0]))
Expand All @@ -47,3 +163,115 @@ public func abs<T: NdArray<Float>>(_ a: T) -> T {
abs(a, out: b)
return b
}

/// see ``Darwin/asinf``.
public func asin<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.asinf)
return b
}

/// see ``Darwin/acosf``.
public func acos<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.acosf)
return b
}

/// see ``Darwin/atanf``.
public func atan<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.atanf)
return b
}

/// see ``Darwin/cosf``.
public func cos<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.cosf)
return b
}

/// see ``Darwin/sinf``.
public func sin<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.sinf)
return b
}

/// see ``Darwin/tanf``.
public func tan<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.tanf)
return b
}

/// see ``Darwin/coshf``.
public func cosh<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.coshf)
return b
}

/// see ``Darwin/sinhf``.
public func sinh<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.sinhf)
return b
}

/// see ``Darwin/tanhf``.
public func tanh<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.tanhf)
return b
}

/// see ``Darwin/expf``.
public func exp<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.expf)
return b
}

/// see ``Darwin/exp2f``.
public func exp2<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.exp2f)
return b
}

/// see ``Darwin/logf``.
public func log<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.logf)
return b
}

/// see ``Darwin/log10f``.
public func log10<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.log10f)
return b
}

/// see ``Darwin/log1pf``.
public func log1p<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.log1pf)
return b
}

/// see ``Darwin/log2f``.
public func log2<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.log2f)
return b
}

/// see ``Darwin/logbf``.
public func logb<T: NdArray<Float>>(_ a: T) -> T {
let b = T(copy: a)
b.apply(Darwin.logbf)
return b
}
Loading

0 comments on commit 734e778

Please sign in to comment.