Group Abstract Group Abstract

Message Boards Message Boards

1
|
8.1K Views
|
22 Replies
|
7 Total Likes
View groups...
Share
Share this post:

What is the pattern for an argument that must be a List of Integers

POSTED BY: Henrick Jeanty
22 Replies
Posted 3 years ago

I forgot to mention that I have opened another thread A pretty general pattern matching test program where I summarized the lessons learned here. I brought them into the form of a program within a notebook. The program is able to test arbitrary patterns against any arguments. Both with MatchQ and as function parameter specifications.

POSTED BY: Werner Geiger
Posted 3 years ago

Thanks, Rohit. Of course there many way to achieve my goal. I wanted to understand why I cannot do it with the simple condition:

f[xs:{(e_/;e∈ℝ&&e>1)...}]

Above Michael Rogers explained that I have to use (unnamed) PatternTest.

BTW: Your definition with "Real | Integer" would miss rationals, hence had to use

_Real | _Integer | _Rational
POSTED BY: Werner Geiger
Posted 3 years ago

Hi Werner,

Hence I cannot define a function that accepts a list of real integers greater than 1.

How about this?

Block[{f},
 f[xs : {a : (_Real | _Integer) ..} /; AllTrue[{a}, # > 1 &]] := xs;
 Print[f[{2., 2, 3 + I}]];
 Print[f[{1., 1}]];
 Print[f[{.5, 2, 3 + 1}]];
 Print[f[{2., 2, 5/2}]];
 Print[f[{2., 1., 3 + 1}]];
 Print[f[{2., 2, 3 + 1}]];
 ]
(*
f[{2.,2,3+I}]
f[{1.,1}]
f[{0.5,2,4}]
f[{2.,2,5/2}]
f[{2.,1.,4}]
{2.,2,4}
*)
POSTED BY: Rohit Namjoshi
Posted 3 years ago
POSTED BY: Werner Geiger
POSTED BY: Michael Rogers
Posted 3 years ago

Great, Michael. I read that restriction "... same expression ....", but did not understand it. Now I learned why and how to use PatternTest.

POSTED BY: Werner Geiger

Even though your question focused on RepeatedNull[], I maybe should have mentioned that

MatchQ[{1.1, 2., 3 + 1}, {_?(# ∈ Reals \[And] # > 1 &) ...}]

can also be done with ___ (BlankNullSequence[]) instead of ...:

MatchQ[{1.1, 2., 3 + 1}, {___?(# ∈ Reals \[And] # > 1 &)}]
POSTED BY: Michael Rogers
Posted 3 years ago

Michael, just another question, concerning PatternTest for testing more than one variable.

As an example I want to match a list of 2D-vectors where y is greater than x. I can write:

MatchQ[{{1, 2}, {Pi, 3.2}}, {_?(#[[1]] < #[[2]] &) ...}]

==> True

But I cannot use a more readable form like:

MatchQ[{{1, 2}, {Pi, 3.2}}, {{_, _}?(#1 < #2 &) ...}]

==> enter image description here Do you know if there is something the like?

POSTED BY: Werner Geiger
POSTED BY: Michael Rogers
Posted 3 years ago

Michael, I'm glad I didn't miss anything. I agree with what you said. Your last suggestion comes closest to the "readability" goal.

Thanks again,

POSTED BY: Werner Geiger
Posted 3 years ago
POSTED BY: Hans Milton
Posted 3 years ago
POSTED BY: Werner Geiger
POSTED BY: Henrick Jeanty

Here's a recursive pattern test that checks for lists of lists of...of lists of integers, that is, of arbitrarily nested lists of integers.

nestedListOfIntegerQ = MatchQ[#, {(_Integer | _?nestedListOfIntegerQ) ...}] &;

f[x_?nestedListOfIntegerQ] := Depth[x];

More examples of nested lists:

MatchQ[{1, 2, 3}, _?nestedListOfIntegerQ]
(*  True  *)

MatchQ[{{1, 2, 3}, {4, 5, 6}}, _?nestedListOfIntegerQ]
(*  True  *)

MatchQ[{{2}, {3, {4}, 5}}, _?nestedListOfIntegerQ]
(*  True  *)

(* Allows empty lists *)
MatchQ[{{}, {{}}}, _?nestedListOfIntegerQ]
(*  True  *)

Use double-dot .. (Repeated) instead of the triple-dot ... (RepeatedNull) to match nested lists, none of which are empty. If you want a mix, you'll have to specify an explicit pattern for the specific mix.

POSTED BY: Michael Rogers

Never thought of that! Thank you! So, is there some sort of repository of pattern expressions for commonly used patterns? Things like patterns for URLs, IP addresses, street addresses, etc...?

POSTED BY: Henrick Jeanty
Posted 3 years ago

So, is there some sort of repository of pattern expressions for commonly used patterns? Things like patterns for URLs, IP addresses, street addresses, etc...?

Not patterns but Interpreter can do that.

POSTED BY: Rohit Namjoshi
Posted 3 years ago

What would be nice would be able to give a pattern a name...

You can certainly do this.

MyPattern = {_String, {__Integer}, _Symbol}

TheSymbols[structs : {MyPattern ...}] := structs[[All, -1]]

TheSymbols[{{"a", RandomInteger[10, 2], abc}, {"b", RandomInteger[10, 2], xyz}}]
(*returns {abc, xyz}*)
POSTED BY: Eric Rimbey
Posted 3 years ago
f[ns : {___Integer}] = whatever  (*this includes an empty list*)
f[ns : {__Integer}] = whatever (*this excludes an empty list*) 
POSTED BY: Eric Rimbey
F[x:{(_Integer)…}] := x ?
POSTED BY: Sander Huisman

That works for a list of Integers. Thank you! But how about an argument that could be a List of List of Integers as in calling F[{{1,2,3},{4,5,6}}] ?

POSTED BY: Henrick Jeanty

You would need to do something like:

F[x_?(ArrayQ[#,1|2,IntegerQ])] :=

Look at pattern testing and ArrayQ

POSTED BY: Sander Huisman

I will do that though I have read a lot about patterns. In any case, something that would be great would be a repository of patterns. Some already exist in the documentation, but we would need more. I know that with regular expressions there are dictionaries of patterns for things like: valid credit card #'s phone #'s etc.. What would be nice would be able to give a pattern a name like ListOfIntegers = {_ _ _Integer} then one could compose larger patterns as in ListOfListOfIntegers = {_ _ _ListOfIntegers } meaning a ListOfListOfIntegers is made up of a list of 1 or more ListsOfIntegers

POSTED BY: Henrick Jeanty
Reply to this discussion
Community posts can be styled and formatted using the Markdown syntax.
Reply Preview
Attachments
Remove
or Discard