Project Euler にチャレンジ:Problem 32 PHPでの解答

← Problem 31  Problem 33 →
感覚的に上手に解けたような気はするけど、きれいに解けた感じがあまりしない。
<?php

// a * b = c のとき、
// a の文字数とb の文字数と c の文字数の合計が9である必要がある。
// a * b = c の場合、c の文字数は a + b または a + b -1 となる。
// 文字数 a + b + c = 9 を満たすならば、a + b + a + b = 9 もしくは a + b + a + b - 1 = 9 である必要がある。
// a , b ,c の文字数は整数なので、 2(a + b) は偶数。 a + b + a + b = 9 はありえない
// a + b + a + b - 1 = 9 である必要がある。 2(a + b) = 10 よって a + b = 5(a >= 1 , b >= 1) である。
// 問題文から、a * b と b * a は同一と考えてよいので、a < b としてよい。a は1桁または2桁、bは3桁または4桁と考えることができる
$sum = array();

for($a = 2 ; $a <= 99 ; $a++)
{
	// 0は使われないので、10,20...は飛ばしてよい。
	if($a % 10 != 0)
	{
		$a_len = strlen($a);
		// aが1桁の時bは4桁、aが2桁の時bは3桁
		if($a_len == 1)
		{	
			$b_max = 9999;
			$b_start = 1000;
		}
		else
		{
			$b_max = 999;
			$b_start = 100;
		}
		for($b = $b_start ; $b <= $b_max ; $b++)
		{
			// aの桁数とb の桁数はの合計は5であるc の桁数は4である必要がある。
			$c = $a * $b;
			if(strlen($c) >= 5)
			{
				break;
			}
			// 全ての文字列が別であればよい。
			$tmp = $a.$b.$c;
			if(strpos($tmp,"1") !== false and strpos($tmp,"2") !== false and strpos($tmp,"3") !== false and strpos($tmp,"4") !== false and strpos($tmp,"5") !== false and strpos($tmp,"6") !== false and strpos($tmp,"7") !== false and strpos($tmp,"8") !== false and strpos($tmp,"9") !== false)
			{
				$sum[] = $c;
			}
		}
	}
}
echo array_sum(array_unique($sum));
	
?>
問題文