パスワードとかに使えそうなランダムな文字列を生成する方法をとりあえずよく使う perl, php, ruby の3つの言語で書いてみました。
使う文字種はアルファベットの小文字、大文字、数字、各種記号を含みます。
流れとしては
というものです。
それではそれぞれの言語でのコードです。
#!/usr/bin/perl
use strict;
sub generate_password {
my $length = shift @_ || 8;
my @seed = (
'a'..'z',
'A'..'Z',
0..9,
'!', '"', '#', '$', '%', '&', "'", '(', ')', '=', '~',
'|', '-', '^', '@', '`', '+', '*', '<', '>', '_'
);
my $str = '';
while(length $str < $length) {
$str .= @seed[int rand(scalar @seed)];
}
return $str;
}
print generate_password . "\n";
<?php
function generate_password($length = 8)
{
$salt = array_merge(
range('a', 'z'),
range('A', 'Z'),
range(0, 9),
array('!', '"', '#', '$', '%', '&', "'", '(', ')', '=', '~'),
array('|', '-', '^', '@', '`', '+', '*', '<', '>', '_')
);
$str = '';
while(strlen($str) < $length) {
$str .= $salt[mt_rand(0, count($salt) - 1)];
}
return $str;
}
echo generate_password() . PHP_EOL;
#!/usr/local/bin/ruby
def generate_password(length = 8)
symbols = [
'!', '"', '#', '$', '%', '&', "'", '(', ')', '=', '~',
'|', '-', '^', '@', '`', '+', '*', '<', '>', '_'
]
seed = ('a'..'z').to_a + ('A'..'Z').to_a + (0..9).to_a + symbols
str = ''
while (str.length < length)
str += seed[rand(seed.length)].to_s
end
str
end
p generate_password
ruby の場合は0-9の配列を作成するときに数字としての配列を作成していると、
文字を連結するときに .to_s メソッドで文字列として連結してやらないと文字列に数字を足そうとして次のようなエラーが起こることがあります。
`+’: can’t convert Fixnum into String (TypeError)
回避方法は上記のように結合時に .to_s を使うか、(0..9).to_a を (‘0’..’9′).to_a として文字の配列にしておくかです。
それぞれのやり方で配列を生成したのを比べるとわかると思います。
p (0..9).to_a # => [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
p ('0'..'9').to_a # => ["0", "1", "2", "3", "4", "5", "6", "7", "8", "9"]
いかがでしょうか。
パスワードを生成したいときにサクッと実行したらかんたんにランダムパスワードが作成できますよ。
各言語別にランダム関数の挙動が異なります。
指定された最大値を含む値を返す => php
指定された最大値を含まない値を返す => perl, ruby
php の場合は mt_rand(0, 10) とすると 0以上10以下(10を含む) の数値を返しますが、
perl, ruby の rand(10) だと 0以上10未満(10を含まない) の数値を返します。