Skip to content

Commit

Permalink
Curried versions of endswith and startswith (#35052)
Browse files Browse the repository at this point in the history
  • Loading branch information
carstenbauer authored Mar 11, 2020
1 parent 55cd761 commit 0a43c0f
Show file tree
Hide file tree
Showing 3 changed files with 79 additions and 0 deletions.
1 change: 1 addition & 0 deletions NEWS.md
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ New library functions
expressions before they are evaluated ([#34595]).
* New function `bitreverse` for reversing the order of bits in a fixed-width integer ([#34791]).
* New function `bitrotate(x, k)` for rotating the bits in a fixed-width integer ([#33937]).
* One argument methods `startswith(x)` and `endswith(x)` have been added, returning partially-applied versions of the functions, similar to existing methods like `isequal(x)` ([#33193]).

New library features
--------------------
Expand Down
30 changes: 30 additions & 0 deletions base/strings/util.jl
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,36 @@ function endswith(a::Union{String, SubString{String}},
end
end

"""
endswith(suffix)
Create a function that checks whether its argument ends with `suffix`, i.e.
a function equivalent to `y -> endswith(y, suffix)`.
The returned function is of type `Base.Fix2{typeof(endswith)}`, which can be
used to implement specialized methods.
!!! compat "Julia 1.5"
The single argument `endswith(suffix)` requires at least Julia 1.5.
"""
endswith(s) = Base.Fix2(endswith, s)

"""
startswith(prefix)
Create a function that checks whether its argument starts with `prefix`, i.e.
a function equivalent to `y -> startswith(y, prefix)`.
The returned function is of type `Base.Fix2{typeof(startswith)}`, which can be
used to implement specialized methods.
!!! compat "Julia 1.5"
The single argument `startswith(prefix)` requires at least Julia 1.5.
"""
startswith(s) = Base.Fix2(startswith, s)

"""
chop(s::AbstractString; head::Integer = 0, tail::Integer = 1)
Expand Down
48 changes: 48 additions & 0 deletions test/strings/basic.jl
Original file line number Diff line number Diff line change
Expand Up @@ -51,71 +51,119 @@ end

@testset "{starts,ends}with" begin
@test startswith("abcd", 'a')
@test startswith('a')("abcd")
@test startswith("abcd", "a")
@test startswith("a")("abcd")
@test startswith("abcd", "ab")
@test startswith("ab")("abcd")
@test !startswith("ab", "abcd")
@test !startswith("abcd")("ab")
@test !startswith("abcd", "bc")
@test !startswith("bc")("abcd")
@test endswith("abcd", 'd')
@test endswith('d')("abcd")
@test endswith("abcd", "d")
@test endswith("d")("abcd")
@test endswith("abcd", "cd")
@test endswith("cd")("abcd")
@test !endswith("abcd", "dc")
@test !endswith("dc")("abcd")
@test !endswith("cd", "abcd")
@test !endswith("abcd")("cd")
@test startswith("ab\0cd", "ab\0c")
@test startswith("ab\0c")("ab\0cd")
@test !startswith("ab\0cd", "ab\0d")
@test !startswith("ab\0d")("ab\0cd")
x = ""
y = String(codeunits(x)[1:2])
z = String(codeunits(x)[1:1])
@test !startswith(x, y)
@test !startswith(y)(x)
@test !startswith(x, z)
@test !startswith(z)(x)
@test !startswith(y, z)
@test !startswith(z)(y)
@test startswith(x, x)
@test startswith(x)(x)
@test startswith(y, y)
@test startswith(y)(y)
@test startswith(z, z)
@test startswith(z)(z)
x = SubString(x)
y = SubString(y)
z = SubString(z)
@test !startswith(x, y)
@test !startswith(y)(x)
@test !startswith(x, z)
@test !startswith(z)(x)
@test !startswith(y, z)
@test !startswith(z)(y)
@test startswith(x, x)
@test startswith(x)(x)
@test startswith(y, y)
@test startswith(y)(y)
@test startswith(z, z)
@test startswith(z)(z)
x = "x∀y"
y = SubString("x\xe2\x88y", 1, 2)
z = SubString("x\xe2y", 1, 2)
@test !startswith(x, y)
@test !startswith(y)(x)
@test !startswith(x, z)
@test !startswith(z)(x)
@test !startswith(y, z)
@test !startswith(z)(y)
@test startswith(x, x)
@test startswith(x)(x)
@test startswith(y, y)
@test startswith(y)(y)
@test startswith(z, z)
@test startswith(z)(z)
x = ""
y = String(codeunits(x)[2:3])
z = String(codeunits(x)[3:3])
@test !endswith(x, y)
@test !endswith(y)(x)
@test !endswith(x, z)
@test !endswith(z)(x)
@test endswith(y, z)
@test endswith(z)(y)
@test endswith(x, x)
@test endswith(x)(x)
@test endswith(y, y)
@test endswith(y)(y)
@test endswith(z, z)
@test endswith(z)(z)
x = SubString(x)
y = SubString(y)
z = SubString(z)
@test !endswith(x, y)
@test !endswith(y)(x)
@test !endswith(x, z)
@test !endswith(z)(x)
@test endswith(y, z)
@test endswith(z)(y)
@test endswith(x, x)
@test endswith(x)(x)
@test endswith(y, y)
@test endswith(y)(y)
@test endswith(z, z)
@test endswith(z)(z)
x = "x∀y"
y = SubString("x\x88\x80y", 2, 4)
z = SubString("x\x80y", 2, 3)
@test !endswith(x, y)
@test !endswith(y)(x)
@test !endswith(x, z)
@test !endswith(z)(x)
@test endswith(y, z)
@test endswith(z)(y)
@test endswith(x, x)
@test endswith(x)(x)
@test endswith(y, y)
@test endswith(y)(y)
@test endswith(z, z)
@test endswith(z)(z)
end

@testset "filter specialization on String issue #32460" begin
Expand Down

0 comments on commit 0a43c0f

Please sign in to comment.