Problem:
MathJax.Hub.Config({ tex2jax: { inlineMath: [["$","$"], ["\\(","\\)"]], processEscapes: true }});

夏合宿の朝は早い

JAG夏合宿の朝は早い．
正確にはそこまで早くないが，早いと感じる参加者が多いという．

例年合宿の会場となる施設では，退去時に参加者がシーツの回収や掃除をしなければならない．
1 つの部屋でも退去が遅れると，来年以降の施設の利用に関わるため，参加者は一人たりとも寝坊してはならない．

そうは言っても皆人間，寝坊することもある．
しかし，起きた人が連絡先を知っている人にモーニングコールをすることで，一人も寝坊しないよう努めることができるはずだ．

JAG夏合宿の運営を任されたあなたは，寝坊を絶対に防ぐ手を打つための前準備として，どのくらいの確率で全員がきちんと起きられるのかを調べることにした．
準備としてまず，各参加者の寝坊する確率と，各々が連絡先を知っている人のリストを入手した．
ここで，部屋は個室であるため，各々が寝坊するか否かは，他の参加者が寝坊するか否かとは独立である．
起きた人は必ずすべての知っている連絡先にモーニングコールをすること，また，モーニングコールを受けた人は必ず起きることを仮定するとき，全員がきちんと起きられる確率をこれらの情報から計算せよ．

Input

入力は複数のデータセットからなる． 各データセットは次の形式で表される．

N
p1 m1 a(1,1) ... a(1, m1)
...
pN mN a(N,1) ... a(N, mN)

N は参加者の数であり，100 を越えない正の整数である．pi は i 番目の参加者の寝坊する確率であり，小数点以下 2 桁以内の 0 以上 1 以下の実数である．mi は i 番目の参加者が知っている連絡先の数であり，0 以上 N 以下の整数である．a(i, j) は i 番目の参加者が知っている j 番目の連絡先が a(i, j) 番目の参加者のものであることを表す．a(i, j) は N を越えない正の整数である．

入力の終わりは，1 つのゼロからなる行で示す．

Output

各データセットについて，全員が起床できる確率を 1 行に出力せよ．出力には 0.00001 以上の誤差を含んではならない．

Sample Input

2
0.60 1 2
0.60 0
2
0.60 1 2
0.60 1 1
5
0.10 1 2
0.20 1 3
0.30 1 4
0.40 1 5
0.50 1 1
5
0.10 0
0.20 1 1
0.30 1 1
0.40 1 1
0.50 1 1
5
0.10 4 2 3 4 5
0.20 0
0.30 0
0.40 0
0.50 0
4
0.10 1 2
0.20 0
0.30 1 4
0.40 1 3
5
0.10 0
0.20 0
0.30 0
0.40 0
0.50 0
0

Output for Sample Input

0.400000000
0.640000000
0.998800000
0.168000000
0.900000000
0.792000000
0.151200000

Solution in Ruby (judge verdict: Accepted)

require 'tsort'
require 'set'

class Hash
    include TSort
    alias tsort_each_node each_key
    def tsort_each_child(u)
        self[u].each do |v|
            yield(v)
        end
    end
end

loop do
    n = gets.to_i
    break if n == 0
    g = {}
    sleep_prob = []
    n.times do |i|
        g[i] = Set.new
        q, _, *neighbours = gets.split.map(&:to_f)
        sleep_prob[i] = q
        neighbours.each do |j|
            g[i] << j.to_i - 1
        end
    end
    scc = g.strongly_connected_components
    dict = {}
    scc.each.with_index do |a, i|
        a.each do |j|
            dict[j] = i
        end
    end

    roots = Set[*(0..scc.size-1).to_a]
    g.each_key do |i|
        g[i].each do |j|
            next if dict[i] == dict[j]
            roots.delete(dict[j])
        end
    end

    ans = roots.map {|i| 1 - scc[i].map {|j| sleep_prob[j]}.inject(:*)}.inject(:*)
    printf("%.9f\n", ans)
end