检查 PHP 枚举是否包含大小写,例如基本(非支持)枚举上的 try() 方法
Check if PHP enum contains case, like try() method on basic (not backed) enumerations
我有基本枚举
enum Fruit
{
case APPLE;
case ORANGE;
case BANANA;
}
以及一些使用该枚举类型的函数:
function eatFruit (Fruit $fruit)
{
// do stuff
}
和未知内容的变量
$fruit = $_POST['fruit']; // user choosed "MILK"
if (?????) { // how to check if it's fruit?
eatFruit($fruit); // this should not be executed
}
我无法在 documentation 中找到检查枚举是否包含特定大小写的简单方法。
像这样的支持枚举是可能的
enum Fruit
{
case APPLE = 'APPLE';
case ORANGE = 'ORANGE';
case BANANA = 'BANANA';
}
Fruit::from('');
Fruit::tryFrom('');
这会起作用,但是 from
在我的第一个示例中的非支持枚举中不存在。
Fatal error: Uncaught Error: Call to undefined method Fruit::from()
您可以为此使用静态方法cases()
。 returns 枚举中所有值的数组。这些值有一个“名称”属性,它是您可以检查的字符串表示形式(后备枚举也有一个“值”属性,其中包含您在枚举中定义的字符串值)。
所以一个示例实现可能是这样的:
enum Fruit {
case APPLE;
case ORANGE;
case BANANA;
}
// String from user input
$fruit = $_POST['fruit'];
// Find matching fruit in all enum cases
$fruits = Fruit::cases();
$matchingFruitIndex = array_search($fruit, array_column($fruits, "name"));
// If found, eat it
if ($matchingFruitIndex !== false) {
$matchingFruit = $fruits[$matchingFruitIndex];
eatFruit($matchingFruit);
} else {
echo $fruit . " is not a valid Fruit";
}
function eatFruit(Fruit $fruit): void {
if ($fruit === Fruit::APPLE) {
echo "An apple a day keeps the doctor away";
} elseif ($fruit === Fruit::ORANGE) {
echo "When life gives you oranges, make orange juice";
} elseif ($fruit === Fruit::BANANA) {
echo "Banana for scale";
}
}
带有示例数据的工作版本:https://3v4l.org/ObD3s
如果你想用不同的枚举更频繁地这样做,你可以为此编写一个辅助函数:
function getEnumValue($value, $enumClass) {
$cases = $enumClass::cases();
$index = array_search($value, array_column($cases, "name"));
if ($index !== false) {
return $cases[$index];
}
return null;
}
$fruit = getEnumValue($_POST['fruit'], Fruit::class);
if ($fruit !== null) {
eatFruit($fruit);
} else {
echo $_POST['fruit'] . " is not a valid Fruit";
}
具有相同样本数据的示例:https://3v4l.org/bL8Wa
我有基本枚举
enum Fruit
{
case APPLE;
case ORANGE;
case BANANA;
}
以及一些使用该枚举类型的函数:
function eatFruit (Fruit $fruit)
{
// do stuff
}
和未知内容的变量
$fruit = $_POST['fruit']; // user choosed "MILK"
if (?????) { // how to check if it's fruit?
eatFruit($fruit); // this should not be executed
}
我无法在 documentation 中找到检查枚举是否包含特定大小写的简单方法。
像这样的支持枚举是可能的
enum Fruit
{
case APPLE = 'APPLE';
case ORANGE = 'ORANGE';
case BANANA = 'BANANA';
}
Fruit::from('');
Fruit::tryFrom('');
这会起作用,但是 from
在我的第一个示例中的非支持枚举中不存在。
Fatal error: Uncaught Error: Call to undefined method Fruit::from()
您可以为此使用静态方法cases()
。 returns 枚举中所有值的数组。这些值有一个“名称”属性,它是您可以检查的字符串表示形式(后备枚举也有一个“值”属性,其中包含您在枚举中定义的字符串值)。
所以一个示例实现可能是这样的:
enum Fruit {
case APPLE;
case ORANGE;
case BANANA;
}
// String from user input
$fruit = $_POST['fruit'];
// Find matching fruit in all enum cases
$fruits = Fruit::cases();
$matchingFruitIndex = array_search($fruit, array_column($fruits, "name"));
// If found, eat it
if ($matchingFruitIndex !== false) {
$matchingFruit = $fruits[$matchingFruitIndex];
eatFruit($matchingFruit);
} else {
echo $fruit . " is not a valid Fruit";
}
function eatFruit(Fruit $fruit): void {
if ($fruit === Fruit::APPLE) {
echo "An apple a day keeps the doctor away";
} elseif ($fruit === Fruit::ORANGE) {
echo "When life gives you oranges, make orange juice";
} elseif ($fruit === Fruit::BANANA) {
echo "Banana for scale";
}
}
带有示例数据的工作版本:https://3v4l.org/ObD3s
如果你想用不同的枚举更频繁地这样做,你可以为此编写一个辅助函数:
function getEnumValue($value, $enumClass) {
$cases = $enumClass::cases();
$index = array_search($value, array_column($cases, "name"));
if ($index !== false) {
return $cases[$index];
}
return null;
}
$fruit = getEnumValue($_POST['fruit'], Fruit::class);
if ($fruit !== null) {
eatFruit($fruit);
} else {
echo $_POST['fruit'] . " is not a valid Fruit";
}
具有相同样本数据的示例:https://3v4l.org/bL8Wa