#include <iostream>
#include <cstdio>
#include <algorithm>
#include <vector>
#include <stack>
using namespace std;

int n, m, a;
double prob;

// Strongly Connected Component
class SCC {
private:
    int n, cmpNum;
    double p[110] = {0.0};
    vector<vector<int> > g, rg, roots, set;
    vector<int> cmp;
    vector<bool> used;
    stack<int> st;

public:
    SCC(int V) : n(V), g(V), rg(V), cmp(V), used(V, false) {}

    void addEdge(int from, int to) {
        g[from].push_back(to);
        rg[to].push_back(from);
    }

    void setProb(int id, double x) {
        p[id] = x;
    }

    void dfs(int v) {
        used[v] = true;
        int size_ = g[v].size();

        for (int i = 0; i < size_; ++i) {
            if (!used[g[v][i]]) dfs(g[v][i]);
        }

        st.push(v);
    }

    void rdfs(int v, int k) {
        used[v] = true;
        cmp[v] = k;
        int size_ = rg[v].size();

        for (int i = 0; i < size_; ++i) {
            if (!used[rg[v][i]]) rdfs(rg[v][i], k);
        }

        st.push(v);
    }

    int scc() {
        for (int i = 0; i < n; ++i) if (!used[i]) dfs(i);

        used.assign(n, false);

        int k = 0;

        while (!st.empty()) {
            if (!used[st.top()]) rdfs(st.top(), k++);
            st.pop();
        }

        cmpNum = k;
        roots.resize(k);
        set.resize(k);
        return k;
    }

    bool same(int x, int y) {
        return (cmp[x] == cmp[y]);
    }

    void splitSet() {
        for (int i = 0; i < n; ++i) {
            //cout << i << "'s cmp is " << cmp[i] << endl;
            set[cmp[i]].push_back(i);
        }
    }

    double solve() {
        double ret = 1.0, tmp;
        int size_;

        splitSet();

        for (int i = 0; i < n; ++i) {
            used.assign(n, false);
            if (!used[i]) rrdfs(i);
        }

        for (int i = 0; i < cmpNum; ++i) {
            //cout << "roots's size " << roots[i].size() << endl;
            if (roots[i].size() == 0) {
                //cout << i << "'s setsize is " << set[i].size() << endl;
                size_ = set[i].size();
                tmp = 1.0;

                for (int j = 0; j < size_; ++j) {
                    //cout << "vertex id is " << set[cmp[i]][j] << endl;
                    tmp *= p[set[i][j]];
                    //cout << "set[" << i << "][" << j << "] is " << set[cmp[i]][j] << " & p is " << p[set[i][j]] << endl;
                }
                //cout << "tmp is " << tmp << endl;
                ret *= (1.0 - tmp);
            }
        }

        return ret;
    }

    void rrdfs(int v) {
        //cout << "now vertex is " << v << endl;
        used[v] = true;
        int size_ = rg[v].size();
        //cout << "now vertex's size is " << size_ << endl;

        for (int i = 0; i < size_; ++i) {
            //cout << "used " << used[rg[v][i]] << endl;
            if (!used[rg[v][i]]) {
                if (cmp[v] != cmp[rg[v][i]]) {
                    roots[cmp[v]].push_back(cmp[rg[v][i]]);
                    //cout << cmp[v] << "'s root is " << cmp[rg[v][i]] << endl;
                }
                //cout << v << " to " << rg[v][i] << endl;
                rrdfs(rg[v][i]);
            }
        }
    }

    void print(int v) {
        cout << cmp[v] << endl;
    }
};

int main() {

    while (scanf("%d", &n), n) {
        SCC s(n);

        for (int i = 0; i < n; ++i) {
            scanf("%lf %d", &prob, &m);
            s.setProb(i, prob);
            for (int j = 0; j < m; ++j) {
                scanf("%d", &a);
                s.addEdge(i, a-1);
            }
        }

        s.scc();

        printf("%.10f\n", s.solve());
    }

    return 0;
}

Measured memory_bytes: 3348