my @arr1 = qw(a b b c d); my @arr2 = qw(c c d e e f); my ($unique1, $common, $unique2) = common_unique(\@arr1, \@arr2); sub common_unique { my (@u_c, %union); exists $union{$_} or $union{$_}-- for @{$_[0]}; no warnings 'uninitialized'; $union{$_} <= 0 and $union{$_}++ for @{$_[1]}; while (my ($key, $value) = each %union) { push @{$u_c[$value+1]}, $key; } return @u_c; }