Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add intercalate to arrays #1678

Merged
merged 1 commit into from Apr 22, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
23 changes: 23 additions & 0 deletions docs/modules/Array.ts.md
Expand Up @@ -87,6 +87,7 @@ Added in v2.0.0
- [flatten](#flatten)
- [fromEitherK](#fromeitherk)
- [fromOptionK](#fromoptionk)
- [intercalate](#intercalate)
- [intersection](#intersection)
- [intersperse](#intersperse)
- [lefts](#lefts)
Expand Down Expand Up @@ -1436,6 +1437,28 @@ export declare const fromOptionK: <A extends readonly unknown[], B>(f: (...a: A)

Added in v2.11.0

## intercalate

Creates a new `Array` placing an element in between members of the input `Array`, then folds the results using the
provided `Monoid`.

**Signature**

```ts
export declare const intercalate: <A>(M: Monoid<A>) => (sep: A) => (as: A[]) => A
```

**Example**

```ts
import * as S from 'fp-ts/string'
import { intercalate } from 'fp-ts/Array'

assert.deepStrictEqual(intercalate(S.Monoid)('-')(['a', 'b', 'c']), 'a-b-c')
```

Added in v2.11.9

## intersection

Creates an array of unique values that are included in all given arrays using a `Eq` for equality
Expand Down
22 changes: 22 additions & 0 deletions docs/modules/NonEmptyArray.ts.md
Expand Up @@ -63,6 +63,7 @@ Added in v2.0.0
- [group](#group)
- [groupBy](#groupby)
- [insertAt](#insertat)
- [intercalate](#intercalate)
- [intersperse](#intersperse)
- [modifyAt](#modifyat)
- [prependAll](#prependall)
Expand Down Expand Up @@ -531,6 +532,27 @@ export declare const insertAt: <A>(i: number, a: A) => (as: A[]) => Option<NonEm

Added in v2.0.0

## intercalate

**Note**. The constraint is relaxed: a `Semigroup` instead of a `Monoid`.

**Signature**

```ts
export declare const intercalate: <A>(S: Se.Semigroup<A>) => (sep: A) => (as: NonEmptyArray<A>) => A
```

**Example**

```ts
import * as S from 'fp-ts/string'
import { intercalate } from 'fp-ts/NonEmptyArray'

assert.deepStrictEqual(intercalate(S.Semigroup)('-')(['a', 'b', 'c']), 'a-b-c')
```

Added in v2.11.9

## intersperse

Places an element in between members of an array
Expand Down
24 changes: 23 additions & 1 deletion docs/modules/ReadonlyArray.ts.md
Expand Up @@ -82,6 +82,7 @@ Added in v2.5.0
- [flatten](#flatten)
- [fromEitherK](#fromeitherk)
- [fromOptionK](#fromoptionk)
- [intercalate](#intercalate)
- [intersection](#intersection)
- [intersperse](#intersperse)
- [lefts](#lefts)
Expand Down Expand Up @@ -970,6 +971,27 @@ export declare const fromOptionK: <A extends readonly unknown[], B>(

Added in v2.11.0

## intercalate

Places an element in between members of an array`, then folds the results using the provided `Monoid`.

**Signature**

```ts
export declare const intercalate: <A>(M: Monoid<A>) => (sep: A) => (as: readonly A[]) => A
```

**Example**

```ts
import * as S from 'fp-ts/string'
import { intercalate } from 'fp-ts/Array'

assert.deepStrictEqual(intercalate(S.Monoid)('-')(['a', 'b', 'c']), 'a-b-c')
```

Added in v2.11.9

## intersection

Creates an array of unique values that are included in all given arrays using a `Eq` for equality
Expand Down Expand Up @@ -1901,7 +1923,7 @@ Added in v2.7.0
**Signature**

```ts
export declare const Foldable: Foldable1<'ReadonlyArray'>
export declare const Foldable: F.Foldable1<'ReadonlyArray'>
```

Added in v2.7.0
Expand Down
22 changes: 22 additions & 0 deletions docs/modules/ReadonlyNonEmptyArray.ts.md
Expand Up @@ -68,6 +68,7 @@ Added in v2.5.0
- [getUnionSemigroup](#getunionsemigroup)
- [group](#group)
- [groupBy](#groupby)
- [intercalate](#intercalate)
- [intersperse](#intersperse)
- [modifyAt](#modifyat)
- [prependAll](#prependall)
Expand Down Expand Up @@ -607,6 +608,27 @@ assert.deepStrictEqual(groupBy((s: string) => String(s.length))(['a', 'b', 'ab']

Added in v2.5.0

## intercalate

**Note**. The constraint is relaxed: a `Semigroup` instead of a `Monoid`.

**Signature**

```ts
export declare const intercalate: <A>(S: Se.Semigroup<A>) => (sep: A) => (as: ReadonlyNonEmptyArray<A>) => A
```

**Example**

```ts
import * as S from 'fp-ts/string'
import { intercalate } from 'fp-ts/ReadonlyNonEmptyArray'

assert.deepStrictEqual(intercalate(S.Semigroup)('-')(['a', 'b', 'c']), 'a-b-c')
```

Added in v2.11.9

## intersperse

Places an element in between members of a `ReadonlyNonEmptyArray`.
Expand Down
15 changes: 15 additions & 0 deletions src/Array.ts
Expand Up @@ -1124,6 +1124,21 @@ export const intersperse = <A>(middle: A): ((as: Array<A>) => Array<A>) => {
return (as) => (isNonEmpty(as) ? f(as) : copy(as))
}

/**
* Creates a new `Array` placing an element in between members of the input `Array`, then folds the results using the
* provided `Monoid`.
*
* @example
* import * as S from 'fp-ts/string'
* import { intercalate } from 'fp-ts/Array'
*
* assert.deepStrictEqual(intercalate(S.Monoid)('-')(['a', 'b', 'c']), 'a-b-c')
*
* @category combinators
* @since 2.11.9
*/
export const intercalate: <A>(M: Monoid<A>) => (sep: A) => (as: Array<A>) => A = RA.intercalate

/**
* Creates a new `Array` rotating the input `Array` by `n` steps.
*
Expand Down
14 changes: 14 additions & 0 deletions src/NonEmptyArray.ts
Expand Up @@ -551,6 +551,20 @@ export const intersperse = <A>(middle: A) => (as: NonEmptyArray<A>): NonEmptyArr
return isNonEmpty(rest) ? pipe(rest, prependAll(middle), prepend(head(as))) : copy(as)
}

/**
* **Note**. The constraint is relaxed: a `Semigroup` instead of a `Monoid`.
*
* @example
* import * as S from 'fp-ts/string'
* import { intercalate } from 'fp-ts/NonEmptyArray'
*
* assert.deepStrictEqual(intercalate(S.Semigroup)('-')(['a', 'b', 'c']), 'a-b-c')
*
* @category combinators
* @since 2.11.9
*/
export const intercalate: <A>(S: Semigroup<A>) => (sep: A) => (as: NonEmptyArray<A>) => A = RNEA.intercalate

/**
* @category combinators
* @since 2.0.0
Expand Down
18 changes: 17 additions & 1 deletion src/ReadonlyArray.ts
Expand Up @@ -13,7 +13,7 @@ import { Eq, fromEquals } from './Eq'
import { Extend1 } from './Extend'
import { Filterable1 } from './Filterable'
import { FilterableWithIndex1, PredicateWithIndex, RefinementWithIndex } from './FilterableWithIndex'
import { Foldable1 } from './Foldable'
import * as F from './Foldable'
import { FoldableWithIndex1 } from './FoldableWithIndex'
import { FromEither1, fromEitherK as fromEitherK_ } from './FromEither'
import { identity, Lazy, pipe } from './function'
Expand Down Expand Up @@ -49,6 +49,7 @@ import {
} from './Witherable'
import { Zero1, guard as guard_ } from './Zero'

import Foldable1 = F.Foldable1
import ReadonlyNonEmptyArray = RNEA.ReadonlyNonEmptyArray

// -------------------------------------------------------------------------------------
Expand Down Expand Up @@ -1012,6 +1013,21 @@ export const intersperse = <A>(middle: A): ((as: ReadonlyArray<A>) => ReadonlyAr
return (as) => (isNonEmpty(as) ? f(as) : as)
}

/**
* Places an element in between members of an array`, then folds the results using the provided `Monoid`.
*
* @example
* import * as S from 'fp-ts/string'
* import { intercalate } from 'fp-ts/Array'
*
* assert.deepStrictEqual(intercalate(S.Monoid)('-')(['a', 'b', 'c']), 'a-b-c')
*
* @category combinators
* @since 2.11.9
*/
export const intercalate: <A>(M: Monoid<A>) => (sep: A) => (as: ReadonlyArray<A>) => A = (M) => (sep) => (as) =>
F.intercalate(M, Foldable)(sep, as)

/**
* Rotate a `ReadonlyArray` by `n` steps.
*
Expand Down
16 changes: 16 additions & 0 deletions src/ReadonlyNonEmptyArray.ts
Expand Up @@ -566,6 +566,22 @@ export const intersperse = <A>(middle: A) => (as: ReadonlyNonEmptyArray<A>): Rea
return isNonEmpty(rest) ? pipe(rest, prependAll(middle), prepend(head(as))) : as
}

/**
* **Note**. The constraint is relaxed: a `Semigroup` instead of a `Monoid`.
*
* @example
* import * as S from 'fp-ts/string'
* import { intercalate } from 'fp-ts/ReadonlyNonEmptyArray'
*
* assert.deepStrictEqual(intercalate(S.Semigroup)('-')(['a', 'b', 'c']), 'a-b-c')
*
* @category combinators
* @since 2.11.9
*/
export const intercalate: <A>(S: Semigroup<A>) => (sep: A) => (as: ReadonlyNonEmptyArray<A>) => A = (S) => (sep) => (
as
) => concatAll(S)(intersperse(sep)(as))

/**
* @category combinators
* @since 2.10.0
Expand Down
9 changes: 9 additions & 0 deletions test/Array.ts
Expand Up @@ -702,6 +702,15 @@ describe('Array', () => {
U.deepStrictEqual(_.intersperse(0)([1, 2, 3, 4]), [1, 0, 2, 0, 3, 0, 4])
})

it('intercalate', () => {
U.deepStrictEqual(_.intercalate(S.Monoid)('-')([]), '')
U.deepStrictEqual(_.intercalate(S.Monoid)('-')(['a']), 'a')
U.deepStrictEqual(_.intercalate(S.Monoid)('-')(['a', 'b', 'c']), 'a-b-c')
U.deepStrictEqual(_.intercalate(S.Monoid)('-')(['a', '', 'c']), 'a--c')
U.deepStrictEqual(_.intercalate(S.Monoid)('-')(['a', 'b']), 'a-b')
U.deepStrictEqual(_.intercalate(S.Monoid)('-')(['a', 'b', 'c', 'd']), 'a-b-c-d')
})

it('zipWith', () => {
U.deepStrictEqual(
_.zipWith([1, 2, 3], ['a', 'b', 'c', 'd'], (n, s) => s + n),
Expand Down
8 changes: 8 additions & 0 deletions test/NonEmptyArray.ts
Expand Up @@ -187,6 +187,14 @@ describe('NonEmptyArray', () => {
U.deepStrictEqual(_.intersperse(0)([1, 2, 3, 4]), [1, 0, 2, 0, 3, 0, 4])
})

it('intercalate', () => {
U.deepStrictEqual(_.intercalate(S.Semigroup)('-')(['a']), 'a')
U.deepStrictEqual(_.intercalate(S.Semigroup)('-')(['a', 'b', 'c']), 'a-b-c')
U.deepStrictEqual(_.intercalate(S.Semigroup)('-')(['a', '', 'c']), 'a--c')
U.deepStrictEqual(_.intercalate(S.Semigroup)('-')(['a', 'b']), 'a-b')
U.deepStrictEqual(_.intercalate(S.Semigroup)('-')(['a', 'b', 'c', 'd']), 'a-b-c-d')
})

it('reverse', () => {
U.deepStrictEqual(_.reverse([1, 2, 3]), [3, 2, 1])
})
Expand Down
9 changes: 9 additions & 0 deletions test/ReadonlyArray.ts
Expand Up @@ -802,6 +802,15 @@ describe('ReadonlyArray', () => {
U.deepStrictEqual(_.intersperse(0)([1, 2, 3, 4]), [1, 0, 2, 0, 3, 0, 4])
})

it('intercalate', () => {
U.deepStrictEqual(_.intercalate(S.Monoid)('-')([]), '')
U.deepStrictEqual(_.intercalate(S.Monoid)('-')(['a']), 'a')
U.deepStrictEqual(_.intercalate(S.Monoid)('-')(['a', 'b', 'c']), 'a-b-c')
U.deepStrictEqual(_.intercalate(S.Monoid)('-')(['a', '', 'c']), 'a--c')
U.deepStrictEqual(_.intercalate(S.Monoid)('-')(['a', 'b']), 'a-b')
U.deepStrictEqual(_.intercalate(S.Monoid)('-')(['a', 'b', 'c', 'd']), 'a-b-c-d')
})

it('rotate', () => {
U.strictEqual(_.rotate(0)(_.empty), _.empty)
U.strictEqual(_.rotate(1)(_.empty), _.empty)
Expand Down
8 changes: 8 additions & 0 deletions test/ReadonlyNonEmptyArray.ts
Expand Up @@ -198,6 +198,14 @@ describe('ReadonlyNonEmptyArray', () => {
U.deepStrictEqual(_.intersperse(0)([1, 2, 3, 4]), [1, 0, 2, 0, 3, 0, 4])
})

it('intercalate', () => {
U.deepStrictEqual(_.intercalate(S.Semigroup)('-')(['a']), 'a')
U.deepStrictEqual(_.intercalate(S.Semigroup)('-')(['a', 'b', 'c']), 'a-b-c')
U.deepStrictEqual(_.intercalate(S.Semigroup)('-')(['a', '', 'c']), 'a--c')
U.deepStrictEqual(_.intercalate(S.Semigroup)('-')(['a', 'b']), 'a-b')
U.deepStrictEqual(_.intercalate(S.Semigroup)('-')(['a', 'b', 'c', 'd']), 'a-b-c-d')
})

it('reverse', () => {
const singleton: _.ReadonlyNonEmptyArray<number> = [1]
U.strictEqual(_.reverse(singleton), singleton)
Expand Down