From the Verilog standard:
The case statement is a multiway decision statement that tests whether an expression matches one of a number of other expressions and branches accordingly.
Syntax:
case_statement ::=
case ( expression )
case_item { case_item } endcase
| casez ( expression )
case_item { case_item } endcase
| casex ( expression )
case_item { case_item } endcase
case_item ::=
expression { , expression } : statement_or_null
| default [ : ] statement_or_null
The main use is to decode something: FSM states, address decoding, data decoding, demultiplexer, instruction decoding and so on.
Examples:
case (separation_i[3:0])
4'd0: filtered <= 12'd0;
4'd1: filtered <= {11'd0, table_out[13:13]};
4'd2: filtered <= {10'd0, table_out[13:12]};
4'd3: filtered <= {9'd0, table_out[13:11]};
default: filtered <= table_out[13:2];
endcase
case (address_0)
0: result_0 <= data_0[0+:4];
1: result_0 <= data_0[4+:4];
2: result_0 <= data_0[8+:4];
3: result_0 <= data_0[12+:4];
4: result_0 <= data_0[16+:4];
5: result_0 <= data_0[20+:4];
6: result_0 <= data_0[24+:4];
7: result_0 <= data_0[28+:4];
default: result_0 <= 0;
endcase