最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

reactjs - Array as case in switch case JavaScript - Stack Overflow

programmeradmin3浏览0评论

How can I use an array as case parameter in switch case?

switch ("value")
  case ArrayOfStrings // check every array item to be match with value
    ...

How can I use an array as case parameter in switch case?

switch ("value")
  case ArrayOfStrings // check every array item to be match with value
    ...
Share Improve this question edited May 27, 2020 at 11:42 Mohammadreza asked May 27, 2020 at 11:37 MohammadrezaMohammadreza 831 gold badge1 silver badge10 bronze badges 7
  • 3 Do you want to check if a specific array is passed or if the array constructor function is passed? The former is not possible in a switch, the latter is possible but rather odd. – VLAZ Commented May 27, 2020 at 11:39
  • 1 Can you give a more detailed example of what you are trying to achieve, such as an example of what ... might be? Is the Array in your example literally the Array type, so you are wanting to switch on the type? – lurker Commented May 27, 2020 at 11:40
  • do yoi have a use case for it? what about the other cases? – Nina Scholz Commented May 27, 2020 at 11:41
  • What is the input for your switch? Is that an array, or are you trying to match one value against an array of values? – Ivar Commented May 27, 2020 at 11:41
  • 2 Clean is quite subjective. I find that way very clean. Maybe your solution would be to not use a switch statement, but you haven't provided enough detail for us to determine that. This looks a bit like an XY problem. – Ivar Commented May 27, 2020 at 11:46
 |  Show 2 more ments

4 Answers 4

Reset to default 8

No.

This

switch ("value") {
  case ArrayOfStrings // check every array item to be match with value
    ...

does not work, because the value of switch and the value of case is checked with a Identity/strict equality operator === parison.

It is not possible to check a value agains a value of the array.

Any other construction, like

switch (true) {
  case ArrayOfStrings.includes("value"):  // check every array item to be match with value

would work, but if you have only to check a single value and not other constraints, you better take

if (ArrayOfStrings.includes("value")) {
    // ...
}

I've a workaround using find :

const CARS = ['RENAULT', 'FORD']
const SUV = ['PORSCHE', 'LAMBUGININININ']
const SCOOTER = ['HONDA']

function select(vehicule) {
  switch (vehicule) {
    // Alternative use `case undefined: return 'precatch undefined`'
    case vehicule !== undefined && CARS.find(_ => _ === vehicule): return 'CARS';
    case vehicule !== undefined && SUV.find(_ => _ === vehicule): return 'SUV'
    case vehicule !== undefined && SCOOTER.find(_ => _ === vehicule): return 'SCOOTER';
    default: return 'noop';
  }
}

['', null, undefined, 'WHATEVER', 'HONDA', 'RENAULT']
  .forEach(_ => console.log(_, ' - ', select(_)))

/**
Expected result:

  -  noop
null  -  noop
undefined  -  noop
WHATEVER  -  noop
HONDA  -  SCOOTER
RENAULT  -  CARS
**/

Not sure how this method is discouraged but sounds not so bad.

Well first I would suggest using if with something like Array.isArray:

if (Array.isArray(value)) {
  // check array items
}

But, if you really want/need to check by paring to Array constructor:

const check = (value) => {
  switch (value.constructor) {
    case Array:
      console.log('array');
      break;

    // For example
    case Number:
      console.log('number');
      break;
  }
}

check(7); // 'number'
check([]); // 'array'

I would really discourage from using this approach though.

In theory, you could do that to distinguish between different constructors.

class ArrayOfStrings extends Array<string> {};
class ArrayOfNumbers extends Array<number> {};

function main(input: ArrayOfStrings | ArrayOfNumbers): void {
  switch (input.constructor) {
    case ArrayOfStrings:
      console.log('It was an array of strings!');
      break;
    default:
       console.log('It was something else');
  }
}

main(new ArrayOfStrings('foo', 'bar')); // Logs 'It was an array of strings!'
main(new ArrayOfNumbers(1, 2)); // Logs 'It was something else'

However, this method has limitations.

  1. It doesn't work with subclassing.
  2. input will be of the same type for each case — as opposed to being discriminated. See TypeScript Playground.
  3. You need to create your arrays by using the new keyword.

It's better to use if statements bined with type guards instead.

发布评论

评论列表(0)

  1. 暂无评论