Binary String pattern matching

Hugo Mills hugo@REDACTED
Thu Dec 10 09:27:55 CET 2020


On Wed, Dec 09, 2020 at 10:00:03PM +0100, Java House wrote:
> yes the binary string is of the format <<"xxx">>
> 
> <<"3123CHF">>
> > <<"341424343EUR">>
> > <<"14143US">>
> >
>  Thank you for the answer.
> So is there any other way?
> erlang provides the binary_to_list, is there any way to achieve the same
> with a list becasue I tried similare patterns with list and it does not
> work e.g
> [V|T] this will always match the first character of the string to V
> and [V|"CHF"] does not work neither.

   You can't pattern-match on either binaries or lists with a
variable-sized component that isn't at the end. To do so with lists
would require that the function head (the pattern match) iterates down
the list, which is an O(n) operation, and thus forbidden in pattern
matching and guard expressions.

   Since you know that the currency symbol is always three characters,
you could do something like this (requires, I think, erlang 23 or later):

Size = size(Text),
<<Value:(Size-3)/binary, Currency:3/binary>> = Text,
currency_to_credits(Value, Currency).

   It doesn't appear to be possible to fit this into a single
pattern-match expression:

1> F = fun(<<Text:(size(Bin)-3)/binary, Tail:3/binary>> = Bin) -> {Text, Tail} end.
* 1: variable 'Bin' is unbound

   Hugo.

> Best
> Nikolas
> 
> Στις Τετ, 9 Δεκ 2020 στις 7:58 μ.μ., ο/η kuna.prime <
> kuna.prime@REDACTED> έγραψε:
> 
> > HI,
> >
> > first of all binary string is of form <<"3123CHF">> and not <<3123CHF>>
> > i'm just stating it in case there was a mistake in the first mail
> >
> > to answer your questio in order to pattern match you need to know the size
> > of field you are matching so
> >
> > <<X:4/binary, "CHF">> = <<"3123CHF">>.
> >
> > will match fist 4 bytes and interpret that as new binary (X).
> >
> >
> > Sent with ProtonMail <https://protonmail.com> Secure Email.
> >
> > ‐‐‐‐‐‐‐ Original Message ‐‐‐‐‐‐‐
> > On Wednesday, December 9, 2020 7:28 PM, Java House <java4dev@REDACTED>
> > wrote:
> >
> > there is a typo in the example
> > currrency_to_credits({cur, << Value , "CHF">>}, Acc)
> >   when Value >= <<"1000">>, Value =< <<"10000">> ->
> >      {chf, Acc + Value };
> > currrency_to_credits({cur, << Value , "EUR">>}, Acc)
> >   when Value >= <<"1000">>, Value =< <<"10000">> ->
> >      {eur, Acc + Value };
> > currrency_to_credits({cur, << Value , "US">>}, Acc)
> >   when Value >= <<"1000">>, Value =< <<"10000">> ->
> >      {us, Acc + Value };
> >
> > Στις Τετ, 9 Δεκ 2020 στις 7:17 μ.μ., ο/η Java House <java4dev@REDACTED>
> > έγραψε:
> >
> >> Hello all
> >>
> >> I am learning Erlang and have stuck to the following problem.
> >> How to write a function with pattern matching when the parameter is a
> >> binary string.
> >>
> >> I have a list of binary strings e.g.
> >> <<3123CHF>>
> >> <<341424343EUR>>
> >> <<14143US>>
> >>
> >> I am trying to create a function that matches according to a pattern.
> >>
> >> currrency_to_credits({cur, <<A, "CHF">>}, Acc)
> >>   when Value >= <<"1000">>, Value =< <<"10000">> ->
> >>      {chf, Acc + A};
> >> currrency_to_credits({cur, <<A, "EUR">>}, Acc)
> >>   when Value >= <<"1000">>, Value =< <<"10000">> ->
> >>      {eur, Acc + A};
> >> currrency_to_credits({cur, <<A, "US">>}, Acc)
> >>   when Value >= <<"1000">>, Value =< <<"10000">> ->
> >>      {us, Acc + A};
> >>
> >> But this does not seem to be the right way.
> >> How can I create a pattern for binary string?
> >> will it work better for list string? How?
> >>
> >> Thank you
> >> Nikolas
> >>
> >
> >

-- 
Hugo Mills             | No names... I want to remain anomalous.
hugo@REDACTED carfax.org.uk |
http://carfax.org.uk/  |
PGP: E2AB1DE4          |


More information about the erlang-questions mailing list