Example #1
0
/* Begin Funtion Definitions */
int main (int argc, const char * argv[]) {

    cl_int error;

    GPUInit(&context, &queue, &is_nvidia, &program, "remap_kern.cl");

    cHash_kernel = clCreateKernel(program, "cellHash_kern", &error);
    remap1_kernel = clCreateKernel(program, "remap1_kern", &error);

    printf("             REMAP\n\n");

    if (is_nvidia) 
       printf("size, Brute Force, CPU kD Tree, CPU Hash1, CPU Hash2, NVIDIA Hash1\n");
    else
       printf("size, Brute Force, CPU kD Tree, CPU Hash1, CPU Hash2, ATI Hash1\n");
    for( int levmx = 1; levmx < 10; levmx++) {
       printf("\nlevmx is %d\n\n",levmx);
       for( int i = 1024; i < 50000000; i *= 2) {
           printf("%d, ", i);
           remaps(i, i, 1.0, (double)levmx, 0.0);
           printf("\n");
       }
    }
    
}
inline void merge_segments_with_function( const volume_ptr<ID>& seg_ptr,
                                          const region_graph_ptr<ID,F> rg_ptr,
                                          std::vector<std::size_t>& counts,
                                          const FN& func,
                                          const M& lowt )
{
    zi::disjoint_sets<ID> sets(counts.size());

    region_graph<ID,F>& rg  = *rg_ptr;

    for ( auto& it: rg )
    {
        std::size_t size = func(std::get<0>(it));

        if ( size == 0 )
        {
            break;
        }

        ID s1 = sets.find_set(std::get<1>(it));
        ID s2 = sets.find_set(std::get<2>(it));

        if ( s1 != s2 && s1 && s2 )
        {
            if ( (counts[s1] < size) || (counts[s2] < size) )
            {
                counts[s1] += counts[s2];
                counts[s2]  = 0;
                ID s = sets.join(s1,s2);
                std::swap(counts[s], counts[s1]);
            }
        }
    }

    std::cout << "Done with merging" << std::endl;

    std::vector<ID> remaps(counts.size());

    ID next_id = 1;

    std::size_t low = static_cast<std::size_t>(lowt);

    for ( ID id = 0; id < counts.size(); ++id )
    {
        ID s = sets.find_set(id);
        if ( s && (remaps[s] == 0) && (counts[s] >= low) )
        {
            remaps[s] = next_id;
            counts[next_id] = counts[s];
            ++next_id;
        }
    }

    counts.resize(next_id);

    std::ptrdiff_t xdim = seg_ptr->shape()[0];
    std::ptrdiff_t ydim = seg_ptr->shape()[1];
    std::ptrdiff_t zdim = seg_ptr->shape()[2];

    std::ptrdiff_t total = xdim * ydim * zdim;

    ID* seg_raw = seg_ptr->data();

    for ( std::ptrdiff_t idx = 0; idx < total; ++idx )
    {
        seg_raw[idx] = remaps[sets.find_set(seg_raw[idx])];
    }

    std::cout << "Done with remapping, total: " << (next_id-1) << std::endl;

    region_graph<ID,F> new_rg;

    for ( auto& it: rg )
    {
        ID s1 = remaps[sets.find_set(std::get<1>(it))];
        ID s2 = remaps[sets.find_set(std::get<2>(it))];

        if ( s1 != s2 && s1 && s2 )
        {
            auto mm = std::minmax(s1,s2);
            new_rg.emplace_back(std::get<0>(it), mm.first, mm.second);
        }
    }

    rg.swap(new_rg);

    std::cout << "Done with updating the region graph, size: "
              << rg.size() << std::endl;
}
inline cube_p<int>
get_segmentation( std::vector<cube_p<real>> affs,
                  real threshold = 0.5 )
{
    // only takes 3D affinity graph
    ZI_ASSERT(affs.size==3);

    vec3i  s = size(*affs[0]);
    size_t n = s[0]*s[1]*s[2];

    cube<real> const & xaff = *affs[0];
    cube<real> const & yaff = *affs[1];
    cube<real> const & zaff = *affs[2];

    zi::disjoint_sets<uint32_t> sets(n+1);
    std::vector<uint32_t>       sizes(n+1);

    cube_p<int> ids_ptr = get_cube<int>(s);
    cube<int> & ids     = *ids_ptr;

    for ( size_t i = 0; i < n; ++i )
    {
        ids.data()[i] = i+1;
        sizes[i+1] = 1;
    }

    typedef std::pair<uint32_t,uint32_t> edge_type;
    std::vector<edge_type> edges;

    // thresholded affinity graph
    for ( size_t z = 0; z < s[0]; ++z )
    {
        for ( size_t y = 0; y < s[1]; ++y )
        {
            for ( size_t x = 0; x < s[2]; ++x )
            {
                long id1 = ids[z][y][x];

                if ( x > 0 )
                {
                    // skip disconnected (black) edges
                    // only count connected (white) edges
                    if ( xaff[z][y][x] > threshold )
                    {
                        long id2 = ids[z][y][x-1];
                        edges.push_back(edge_type(id1, id2));
                    }
                }

                if ( y > 0 )
                {
                    // skip disconnected (black) edges
                    // only count connected (white) edges
                    if ( yaff[z][y][x] > threshold )
                    {
                        long id2 = ids[z][y-1][x];
                        edges.push_back(edge_type(id1, id2));
                    }
                }

                if ( z > 0 )
                {
                    // skip disconnected (black) edges
                    // only count connected (white) edges
                    if ( zaff[z][y][x] > threshold )
                    {
                        long id2 = ids[z-1][y][x];
                        edges.push_back(edge_type(id1, id2));
                    }
                }
            }
        }
    }

    // connected components of the thresholded affinity graph
    // computed the size of each connected component
    for ( auto& e: edges )
    {
        uint32_t set1 = sets.find_set(e.first);
        uint32_t set2 = sets.find_set(e.second);

        if ( set1 != set2 )
        {
            uint32_t new_set = sets.join(set1, set2);

            sizes[set1] += sizes[set2];
            sizes[set2]  = 0;

            std::swap(sizes[new_set], sizes[set1]);
        }
    }

    std::vector<uint32_t> remaps(n+1);

    uint32_t next_id = 1;

    // assign a unique segment ID to each of
    // the pixel in a connected component
    for ( size_t i = 0; i < n; ++i )
    {
        uint32_t id = sets.find_set(ids.data()[i]);
        if ( sizes[id] > 1 )
        {
            if ( remaps[id] == 0 )
            {
                remaps[id]    = next_id;
                ids.data()[i] = next_id;
                ++next_id;
            }
            else
            {
                ids.data()[i] = remaps[id];
            }
        }
        else
        {
            remaps[id]    = 0;
            ids.data()[i] = 0;
        }
    }

    return ids_ptr;
}
Example #4
0
inline std::vector<double>
merge_segments_with_function_err( const volume_ptr<ID>& seg_ptr,
                                  const volume_ptr<ID>& gt_ptr,
                                  const region_graph_ptr<ID,F> rg_ptr,
                                  std::vector<std::size_t>& counts,
                                  const FN& func,
                                  const M& lowt )
{
    std::vector<double> ret;

    std::ptrdiff_t xdim = seg_ptr->shape()[0];
    std::ptrdiff_t ydim = seg_ptr->shape()[1];
    std::ptrdiff_t zdim = seg_ptr->shape()[2];

    volume<ID>& seg = *seg_ptr;
    volume<ID>& gt  = *gt_ptr;

    zi::disjoint_sets<ID> sets(counts.size());

    std::size_t tot = 0;

    std::vector<std::size_t> s_i(counts.size());
    std::map<ID,std::size_t> t_j;

    std::vector<std::map<ID,std::size_t>> p_ij(counts.size());

    for ( std::ptrdiff_t z = 0; z < zdim; ++z )
        for ( std::ptrdiff_t y = 0; y < ydim; ++y )
            for ( std::ptrdiff_t x = 0; x < xdim; ++x )
            {
                uint32_t sgv = seg[x][y][z];
                uint32_t gtv =  gt[x][y][z];

                if ( gtv )
                {
                    tot += 1;

                    ++p_ij[sgv][gtv];

                    ++s_i[sgv];
                    ++t_j[gtv];
                }
            }

    double sum_p_ij = 0;
    for ( auto& a: p_ij )
    {
        for ( auto& b: a )
        {
            sum_p_ij += (static_cast<double>(b.second) / tot) *
                (static_cast<double>(b.second) / tot);
        }
    }

    double sum_t_k = 0;
    for ( auto& a: t_j )
    {
        sum_t_k += (static_cast<double>(a.second) / tot) *
            (static_cast<double>(a.second) / tot);
    }


    double sum_s_k = 0;
    for ( auto& a: s_i )
    {
        sum_s_k += (static_cast<double>(a) / tot) *
            (static_cast<double>(a) / tot);
    }

    ret.push_back(sum_p_ij/sum_t_k);
    ret.push_back(sum_p_ij/sum_s_k);

    region_graph<ID,F>& rg  = *rg_ptr;

    int mod = 0;

    F minf = 0;

    for ( auto& it: rg )
    {
        std::size_t size = func(std::get<0>(it));

        if ( size == 0 )
        {
            minf = std::get<0>(it);
            break;
        }

        ID s1 = sets.find_set(std::get<1>(it));
        ID s2 = sets.find_set(std::get<2>(it));

        if ( s1 != s2 && s1 && s2 )
        {
            if ( (counts[s1] < size) || (counts[s2] < size) )
            {
                counts[s1] += counts[s2];
                counts[s2]  = 0;

                sum_s_k -= (static_cast<double>(s_i[s1])/tot) *
                    (static_cast<double>(s_i[s1])/tot);

                sum_s_k -= (static_cast<double>(s_i[s2])/tot) *
                    (static_cast<double>(s_i[s2])/tot);

                s_i[s1] += s_i[s2];
                s_i[s2]  = 0;

                sum_s_k += (static_cast<double>(s_i[s1])/tot) *
                    (static_cast<double>(s_i[s1])/tot);


                for ( auto& b: p_ij[s1] )
                {
                    sum_p_ij -= (static_cast<double>(b.second) / tot) *
                        (static_cast<double>(b.second) / tot);
                }

                for ( auto& b: p_ij[s2] )
                {
                    sum_p_ij -= (static_cast<double>(b.second) / tot) *
                        (static_cast<double>(b.second) / tot);
                    p_ij[s1][b.first] += b.second;
                }

                for ( auto& b: p_ij[s1] )
                {
                    sum_p_ij += (static_cast<double>(b.second) / tot) *
                        (static_cast<double>(b.second) / tot);
                }

                p_ij[s2].clear();

                if ( (++mod) % 100 == 0 )
                {
                    //std::cout << "Now Error: " << (sum_p_ij/sum_t_k) << " "
                    //          << (sum_p_ij/sum_s_k) << "\n";
                    ret.push_back(sum_p_ij/sum_t_k);
                    ret.push_back(sum_p_ij/sum_s_k);
                }


                ID s = sets.join(s1,s2);
                std::swap(counts[s], counts[s1]);
                std::swap(s_i[s], s_i[s1]);
                std::swap(p_ij[s], p_ij[s1]);
            }
        }
    }

    std::cout << "Done with merging" << std::endl;


    for ( auto& it: rg )
    {
        break;

        if (  minf > std::get<0>(it) )
        {
            break;
        }


        ID s1 = sets.find_set(std::get<1>(it));
        ID s2 = sets.find_set(std::get<2>(it));

        if ( s1 != s2 && s1 && s2 )
        {
            //if ( (counts[s1] < 100) || (counts[s2] < 100) )
            {
                counts[s1] += counts[s2];
                counts[s2]  = 0;

                sum_s_k -= (static_cast<double>(s_i[s1])/tot) *
                    (static_cast<double>(s_i[s1])/tot);

                sum_s_k -= (static_cast<double>(s_i[s2])/tot) *
                    (static_cast<double>(s_i[s2])/tot);

                s_i[s1] += s_i[s2];
                s_i[s2]  = 0;

                sum_s_k += (static_cast<double>(s_i[s1])/tot) *
                    (static_cast<double>(s_i[s1])/tot);


                for ( auto& b: p_ij[s1] )
                {
                    sum_p_ij -= (static_cast<double>(b.second) / tot) *
                        (static_cast<double>(b.second) / tot);
                }

                for ( auto& b: p_ij[s2] )
                {
                    sum_p_ij -= (static_cast<double>(b.second) / tot) *
                        (static_cast<double>(b.second) / tot);
                    p_ij[s1][b.first] += b.second;
                }

                for ( auto& b: p_ij[s1] )
                {
                    sum_p_ij += (static_cast<double>(b.second) / tot) *
                        (static_cast<double>(b.second) / tot);
                }

                p_ij[s2].clear();

                //if ( (++mod) % 100 == 0 )
                std::cout << "Now Error: " << (sum_p_ij/sum_t_k) << " "
                          << (sum_p_ij/sum_s_k) << "\n";
                ret.push_back(sum_p_ij/sum_t_k);
                ret.push_back(sum_p_ij/sum_s_k);


                ID s = sets.join(s1,s2);
                std::swap(counts[s], counts[s1]);
                std::swap(s_i[s], s_i[s1]);
                std::swap(p_ij[s], p_ij[s1]);
            }
        }
    }

    std::cout << "Done with merging" << std::endl;


    std::vector<ID> remaps(counts.size());

    ID next_id = 1;

    std::size_t low = static_cast<std::size_t>(lowt);

    for ( ID id = 0; id < counts.size(); ++id )
    {
        ID s = sets.find_set(id);
        if ( s && (remaps[s] == 0) && (counts[s] >= low) )
        {
            remaps[s] = next_id;
            counts[next_id] = counts[s];
            ++next_id;
        }
    }

    counts.resize(next_id);

    std::ptrdiff_t total = xdim * ydim * zdim;

    ID* seg_raw = seg_ptr->data();

    for ( std::ptrdiff_t idx = 0; idx < total; ++idx )
    {
        seg_raw[idx] = remaps[sets.find_set(seg_raw[idx])];
    }

    std::cout << "Done with remapping, total: " << (next_id-1) << std::endl;

    region_graph<ID,F> new_rg;

    std::vector<std::set<ID>> in_rg;

    for ( auto& it: rg )
    {
        ID s1 = remaps[sets.find_set(std::get<1>(it))];
        ID s2 = remaps[sets.find_set(std::get<2>(it))];

        if ( s1 != s2 && s1 && s2 )
        {
            auto mm = std::minmax(s1,s2);
            if ( in_rg[mm.first].count(mm.second) == 0 )
            {
                new_rg.emplace_back(std::get<0>(it), mm.first, mm.second);
                in_rg[mm.first].insert(mm.second);
            }
        }
    }

    rg.swap(new_rg);

    std::cout << "Done with updating the region graph, size: "
              << rg.size() << std::endl;

    return ret;
}
Example #5
0
inline void merge_segments( const volume_ptr<ID>& seg_ptr,
                            const region_graph_ptr<ID,F> rg_ptr,
                            std::vector<std::size_t>& counts,
                            const L& tholds,
                            const M& lowt )
{
    zi::disjoint_sets<ID> sets(counts.size());

    typename region_graph<ID,F>::iterator rit = rg_ptr->begin();

    region_graph<ID,F>& rg  = *rg_ptr;

    for ( auto& it: tholds )
    {
        std::size_t size = static_cast<std::size_t>(it.first);
        F           thld = static_cast<F>(it.second);

        while ( (rit != rg.end()) && ( std::get<0>(*rit) > thld) )
        {
            ID s1 = sets.find_set(std::get<1>(*rit));
            ID s2 = sets.find_set(std::get<2>(*rit));

            if ( s1 != s2 && s1 && s2 )
            {
                if ( (counts[s1] < size) || (counts[s2] < size) )
                {
                    counts[s1] += counts[s2];
                    counts[s2]  = 0;
                    ID s = sets.join(s1,s2);
                    std::swap(counts[s], counts[s1]);
                }
            }
            ++rit;
        }
    }

    std::cout << "Done with merging" << std::endl;

    std::vector<ID> remaps(counts.size());

    ID next_id = 1;

    std::size_t low = static_cast<std::size_t>(lowt);

    for ( ID id = 0; id < counts.size(); ++id )
    {
        ID s = sets.find_set(id);
        if ( s && (remaps[s] == 0) && (counts[s] >= low) )
        {
            remaps[s] = next_id;
            counts[next_id] = counts[s];
            ++next_id;
        }
    }

    counts.resize(next_id);

    std::ptrdiff_t xdim = seg_ptr->shape()[0];
    std::ptrdiff_t ydim = seg_ptr->shape()[1];
    std::ptrdiff_t zdim = seg_ptr->shape()[2];

    std::ptrdiff_t total = xdim * ydim * zdim;

    ID* seg_raw = seg_ptr->data();

    for ( std::ptrdiff_t idx = 0; idx < total; ++idx )
    {
        seg_raw[idx] = remaps[sets.find_set(seg_raw[idx])];
    }

    std::cout << "Done with remapping, total: " << (next_id-1) << std::endl;

    region_graph<ID,F> new_rg;

    std::vector<std::set<ID>> in_rg;

    for ( auto& it: rg )
    {
        ID s1 = remaps[sets.find_set(std::get<1>(it))];
        ID s2 = remaps[sets.find_set(std::get<2>(it))];

        if ( s1 != s2 && s1 && s2 )
        {
            auto mm = std::minmax(s1,s2);
            if ( in_rg[mm.first].count(mm.second) == 0 )
            {
                new_rg.emplace_back(std::get<0>(it), mm.first, mm.second);
                in_rg[mm.first].insert(mm.second);
            }
        }
    }

    rg.swap(new_rg);

    std::cout << "Done with updating the region graph, size: "
              << rg.size() << std::endl;
}
Example #6
0
inline void yet_another_watershed( const volume_ptr<ID>& seg_ptr,
                                   const region_graph_ptr<ID,F> rg_ptr,
                                   std::vector<std::size_t>& counts,
                                   const L& lowl)
{
    F low = static_cast<F>(lowl);

    std::vector<std::size_t> new_counts({0});
    std::vector<ID>          remaps(counts.size());

    zi::disjoint_sets<ID>    sets(counts.size());
    std::vector<F>           maxs(counts.size());


    region_graph<ID,F>& rg  = *rg_ptr;

    ID next_id = 1;
    ID merged = 0;


    for ( auto& it: rg )
    {
        if ( std::get<0>(it) <= low )
        {
            break;
        }

        ID s1 = std::get<1>(it);
        ID s2 = std::get<2>(it);

        F f = std::get<0>(it);

        if ( s1 && s2 )
        {
            if ( (remaps[s1] == 0) || (remaps[s2] == 0) )
            {
                if ( remaps[s1] == 0 )
                {
                    std::swap(s1,s2);
                }

                if ( remaps[s1] == 0 )
                {
                    maxs[next_id] = f;
                    remaps[s1] = remaps[s2] = next_id;
                    new_counts.push_back(counts[s1]+counts[s2]);
                    ++next_id;
                }
                else
                {
                    ID actual = sets.find_set(remaps[s1]);
                    remaps[s2] = remaps[s1];
                    new_counts[actual] += counts[s2];
                }
            }
            else
            {
                ID a1 = sets.find_set(remaps[s1]);
                ID a2 = sets.find_set(remaps[s2]);

                if ( 0 && a1 != a2 && ((maxs[a1]==f)||(maxs[a2]==f)) )
                {
                    ++merged;
                    new_counts[a1] += new_counts[a2];
                    new_counts[a2] = 0;
                    maxs[a1] = std::max(maxs[a1],maxs[a2]);
                    maxs[a2] = 0;
                    ID a = sets.join(a1,a2);
                    std::swap(new_counts[a], new_counts[a1]);
                    std::swap(maxs[a], maxs[a1]);
                }
            }
        }
    }

    next_id -= merged;

    std::vector<ID> remaps2(counts.size());

    next_id = 1;

    for ( ID id = 0; id < counts.size(); ++id )
    {
        ID s = sets.find_set(remaps[id]);
        if ( s && (remaps2[s]==0) )
        {
            remaps2[s] = next_id;
            new_counts[next_id] = new_counts[s];
            ++next_id;
        }
    }

    new_counts.resize(next_id);

    std::ptrdiff_t xdim = seg_ptr->shape()[0];
    std::ptrdiff_t ydim = seg_ptr->shape()[1];
    std::ptrdiff_t zdim = seg_ptr->shape()[2];

    std::ptrdiff_t total = xdim * ydim * zdim;

    ID* seg_raw = seg_ptr->data();

    for ( std::ptrdiff_t idx = 0; idx < total; ++idx )
    {
        seg_raw[idx] = remaps2[remaps[seg_raw[idx]]];
    }

    region_graph<ID,F> new_rg;

    for ( auto& it: rg )
    {
        ID s1 = remaps2[remaps[std::get<1>(it)]];
        ID s2 = remaps2[remaps[std::get<2>(it)]];

        if ( s1 != s2 && s1 && s2 )
        {
            auto mm = std::minmax(s1,s2);
            new_rg.emplace_back(std::get<0>(it), mm.first, mm.second);
        }
    }

    rg.swap(new_rg);

    counts.swap(new_counts);

    std::cout << "New count: " << counts.size() << std::endl;

    std::cout << "Done with updating the region graph, size: "
              << rg.size() << std::endl;
}