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

How to check if an array contains a value? #1037

Open
msarrel opened this issue Jun 19, 2023 · 3 comments
Open

How to check if an array contains a value? #1037

msarrel opened this issue Jun 19, 2023 · 3 comments
Labels

Comments

@msarrel
Copy link

msarrel commented Jun 19, 2023

What is the allowable syntax for conditional expressions?

I have to test if a field is equal to any one of 63 values. The only way I can think to do this is the following, where x1, x2, x3 etc. are integers and a is the field id.

if: a==x1 or a==x2 or a==x3 or ... or a==x63

There has to be a shorter way. Maybe something like list inclusion?

if: a in [x1, x2, x3, ..., x63]
@KOLANICH
Copy link

There is no shorter way. But +1 for set matching. And -1 for the syntax proposed. IMHO we should move to the direction of dict-based syntax for expressions.

@msarrel
Copy link
Author

msarrel commented Jun 19, 2023

Thanks for the answer, even if it isn't what I had hoped for...

@generalmimon
Copy link
Member

generalmimon commented Jun 23, 2023

@msarrel:

There has to be a shorter way. Maybe something like list inclusion?

As @KOLANICH points out, there is no dedicated built-in way in the expression language other than the or chain like in your first sninpet. Probably it makes sense to add it eventually, but it's more of a low priority issue.

If we will ever implement this feature, it would be nice to make it work for ranges (which don't exist in Kaitai Struct yet, but were proposed in #130) and perhaps enums (#518), too.

Currently we have only valid/any-of as a part of #435 (but that's only for validation, i.e. the parsing ends with a validation error if the parsed value didn't match), but it's basically a syntactic sugar for v == 1 or v == 2 or ... as well.

However, with a bit of ingenuity, you can actually implement the list inclusion operation yourself, but I'll let you decide for yourself whether this counts as a "shorter" way:

seq:
  - id: match_steps
    type: 'match_step(known_values[_index], _index != 0 ? match_steps[_index - 1].is_known : false)'
    repeat: expr
    repeat-expr: known_values.size
instances:
  a:
    value: 42
  known_values:
    value: '[1, 2, 42, 46]'
  is_a_in_known_values:
    value: match_steps.last.is_known
types:
  match_step:
    -webide-representation: '{is_known}'
    params:
      - id: cur_known_value
        type: s4
      - id: prev_is_known
        type: bool
    instances:
      is_known:
        value: prev_is_known or _parent.a == cur_known_value

Result (see https://ide.kaitai.io/):

├─ matchSteps
│  ├─ 0 [MatchStep]: false
│  ├─ 1 [MatchStep]: false
│  ├─ 2 [MatchStep]: true
│  └─ 3 [MatchStep]: true
├─ a = 42
├─ knownValues
│  ├─ 0 = 1
│  ├─ 1 = 2
│  ├─ 2 = 42
│  └─ 3 = 46
└─ isAInKnownValues = true

@generalmimon generalmimon changed the title Syntax for conditional expressions? How to check if an array contains a value? Mar 24, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

3 participants