switch statements are usually underrepresented, at least in PHP code. But they don’t have to be and have some nifty features, which makes life easier.

What is the switch statement?

The switch statement is similar to multiple if statements, but it always check for the same condition. Also, if you have to check for a condition multiple times, switch usually is considered looking cleaner and easier to understand than having multiple if statements, as the following example shows:

if ( $type == 'foo' ) {
	$object = new Foo();
}
else if ( $type == 'bar' ) {
	$object = new Bar();
}
else if ( $type == 'foobar' ) {
	$object = new Foobar();
}
else if ( $type == 'baz' ) {
	$object = new Baz();
}
else {
	$object = null;
}Code language: PHP (php)

As a switch statement, it looks like this:

switch ( $type ) {
	case 'foo':
		$object = new Foo();
		break;
	case 'bar':
		$object = new Bar();
		break;
	case 'foobar':
		$object = new Foobar();
		break;
	case 'baz':
		$object = new Baz();
		break;
	default:
		$object = null;
		break;
}Code language: PHP (php)

Usually, I would use strict type comparison in my if statements, but since switch does not use strict type comparison, these both codes are only equivalent in their output this way.

One special feature of the switch statement is that it can work with a default if no other case matches. This is similar to an else statement in an if clause.

Also, you can combine multiple case statements to execute the identical code, working as logical OR:

switch ( $type ) {
	case 'foo':
	case 'bar':
	case 'foobar':
		$object = new Foobar();
		break;
	case 'baz':
		$object = new Baz();
		break;
	default:
		$object = null;
		break;
}Code language: PHP (php)

This will always create a new instance of Foobar if $type is foo, bar or foobar.

When not to use break?

The break statement stops the code at this point inside a case and continues with the code after the switch statement. In the example above, it means that the $object is always assigned only once, since it’s stopping the switch execution afterwards and continues with the following code. You can, however, also omit the break at any time, meaning that the code continues to run, but not comparing to other case statements. I’m using it in the migration code of Embed Privacy, which looks like this:

switch ( $version ) {
	case '1.2.0':
		$this->migrate_1_2_1();
	case '1.2.1':
		$this->migrate_1_2_2();
	case '1.2.2':
		$this->migrate_1_3_0();
	case '1.3.0':
		$this->migrate_1_4_0();
	case '1.4.0':
		$this->migrate_1_4_7();
	case '1.4.7':
		$this->migrate_1_5_0();
	case '1.5.0':
		$this->migrate_1_6_0();
	case '1.6.0':
		$this->migrate_1_7_0();
	case '1.7.0':
		$this->migrate_1_7_3();
	case '1.7.3':
		$this->migrate_1_8_0();
	case '1.8.0':
		$this->migrate_1_10_5();
	case '1.10.5':
		$this->migrate_1_10_6();
	case '1.10.6':
	case '1.10.7':
		$this->migrate_1_10_7();
	case '1.10.9':
		$this->migrate_1_11_0();
	case $this->version:
		// most recent version, do nothing
		break;
	default:
		// run all migrations
		$this->migrate_1_2_0();
		break;
}Code language: PHP (php)

Here, when having $version with the value 1.7.0 for instance, I run all migrations from this point on:

  • $this->migrate_1_7_3();
  • $this->migrate_1_8_0();
  • $this->migrate_1_10_5();
  • $this->migrate_1_10_6();
  • $this->migrate_1_10_7();
  • $this->migrate_1_11_0();

It ignores the later case statements completely and stops only on the first break. This way, I can make sure that even if the current used version is not the next older one comparing to the current version, all migrations from this point are running.

When to use switch( true )?

The switch( true ) statement compares every case with true. This can be used to compare more complex conditions:

switch ( true ) {
	case $type === 'foo':
		$object = new Foo();
		break;
	case $version === '1.2.0':
		$object = new Bar();
		break;
	case $type === 'foobar' && $version === '1.3.0':
		$object = new Foobar();
		break;
}Code language: PHP (php)

This way, you can compare practically everything inside a switch statement and even use strict type comparison.

More examples

You can find more examples in the PHP Manual and especially in the comments there.

Reposts

Leave a Reply

Your email address will not be published. Required fields are marked *

To respond on your own website, enter the URL of your response which should contain a link to this post's permalink URL. Your response will then appear (possibly after moderation) on this page. Want to update or remove your response? Update or delete your post and re-enter your post's URL again. (Learn more about webmentions)