def condense_labels(Z, numsegs, labels): # project all labels at a given Z into a single plane, then merge any that # end up mapping to the same projected subregions (merge = remove one of # them) # # Regions in the presegmentations tend to be similar. This step merges # segments that differ only near the boundaries. # work by chunks for speed. Note that this approach splits projected # segments at chunk boundaries, but since we're just using them for # identifying similar regions, this is fine. overlap_counter = fast64counter.ValueCountInt64() sublabel_offset = 0 for xslice, yslice in work_by_chunks(labels): chunklabels = [labels[yslice, xslice, S, Z][...] for S in range(numsegs)] projected = chunklabels[0] > 0 for S in range(1, numsegs): projected &= chunklabels[S] > 0 # Mask out boundaries labeled_projected, num_found = ndimage_label(projected, output=np.int32) labeled_projected[labeled_projected > 0] += sublabel_offset sublabel_offset += num_found for sub in chunklabels: overlap_counter.add_values_pair32(labeled_projected.ravel(), sub.ravel()) # Build original label to set of projected label map projected_labels, original_labels, areas = overlap_counter.get_counts_pair32() label_to_projected = defaultdict(set) for pl, ol in zip(projected_labels, original_labels): if ol and pl: label_to_projected[ol].add(pl) # Reverse the map projected_to_label = defaultdict(list) for ol, plset in label_to_projected.iteritems(): projected_to_label[tuple(sorted(plset))].append(ol) # Build a remapper to remove merged labels remapper = np.arange(np.max(original_labels) + 1) for original_label_list in projected_to_label.itervalues(): # keep the first, but zero the rest if len(original_label_list) > 1: remapper[original_label_list[1:]] = 0 # pack the labels in the remapper final_label_count = np.sum(remapper > 0) remapper[0] = 1 # simplify next line remapper[remapper > 0] = np.arange(final_label_count + 1, dtype=np.int32) # remap the labels by chunk for xslice, yslice in work_by_chunks(labels): for S in range(numsegs): l = labels[yslice, xslice, S, Z] labels[yslice, xslice, S, Z] = remapper[l] if DEBUG: assert len(np.unique(labels[:, :, :, Z].ravel())) == final_label_count + 1 return final_label_count
sys.exit(0) except Exception, e: print e pass condense_labels = timed(overlaps.condense_labels) lf = h5py.File(output_path + '_partial', 'w') chunking = [chunksize, chunksize, 1, 1] labels = lf.create_dataset('seglabels', segmentations.shape, dtype=np.int32, chunks=tuple(chunking), compression='gzip') total_regions = 0 cross_Z_offset = 0 for Z in range(numslices): this_slice_offset = 0 for seg_idx in range(numsegs): temp, numregions = ndimage_label(1 - segmentations[:, :, seg_idx, Z][...], output=np.int32) labels[:, :, seg_idx, Z] = temp offset_labels(Z, seg_idx, labels, this_slice_offset) this_slice_offset += numregions total_regions += numregions condensed_count = condense_labels(Z, numsegs, labels) print "Labeling depth %d: original %d, condensed %d" % (Z, this_slice_offset, condensed_count) for seg_idx in range (numsegs): offset_labels(Z, seg_idx, labels, cross_Z_offset) cross_Z_offset += condensed_count # XXX - apply cross-D offset print "Labeling took", int(time.time() - st), "seconds, ", condense_labels.total_time, "in condensing" print cross_Z_offset, "total labels", total_regions, "before condensing" if DEBUG: assert np.max(labels) == cross_Z_offset
def condense_labels(Z, numsegs, labels): # project all labels at a given Z into a single plane, then merge any that # end up mapping to the same projected subregions (merge = remove one of # them) # # Regions in the presegmentations tend to be similar. This step merges # segments that differ only near the boundaries. # work by chunks for speed. Note that this approach splits projected # segments at chunk boundaries, but since we're just using them for # identifying similar regions, this is fine. overlap_counter = fast64counter.ValueCountInt64() sublabel_offset = 0 for xslice, yslice in work_by_chunks(labels): chunklabels = [ labels[yslice, xslice, S, Z][...] for S in range(numsegs) ] projected = chunklabels[0] > 0 for S in range(1, numsegs): projected &= chunklabels[S] > 0 # Mask out boundaries labeled_projected, num_found = ndimage_label(projected, output=np.int32) labeled_projected[labeled_projected > 0] += sublabel_offset sublabel_offset += num_found for sub in chunklabels: overlap_counter.add_values_pair32(labeled_projected.ravel(), sub.ravel()) # Build original label to set of projected label map projected_labels, original_labels, areas = overlap_counter.get_counts_pair32( ) label_to_projected = defaultdict(set) for pl, ol in zip(projected_labels, original_labels): if ol and pl: label_to_projected[ol].add(pl) # Reverse the map projected_to_label = defaultdict(list) for ol, plset in label_to_projected.iteritems(): projected_to_label[tuple(sorted(plset))].append(ol) # Build a remapper to remove merged labels remapper = np.arange(np.max(original_labels) + 1) for original_label_list in projected_to_label.itervalues(): # keep the first, but zero the rest if len(original_label_list) > 1: remapper[original_label_list[1:]] = 0 # pack the labels in the remapper final_label_count = np.sum(remapper > 0) remapper[0] = 1 # simplify next line remapper[remapper > 0] = np.arange(final_label_count + 1, dtype=np.int32) # remap the labels by chunk for xslice, yslice in work_by_chunks(labels): for S in range(numsegs): l = labels[yslice, xslice, S, Z] labels[yslice, xslice, S, Z] = remapper[l] if DEBUG: assert len(np.unique(labels[:, :, :, Z].ravel())) == final_label_count + 1 return final_label_count
lf.close() sys.exit(0) except Exception, e: pass condense_labels = timed(overlaps.condense_labels) lf = h5py.File(output_path + '_partial', 'w') chunking = [1, 1, chunksize, chunksize] labels = lf.create_dataset('seglabels', segmentations.shape, dtype=np.int32, chunks=tuple(chunking), compression='gzip') total_regions = 0 cross_D_offset = 0 for D in range(depth): this_D_offset = 0 for Seg in range(numsegs): temp, numregions = ndimage_label(segmentations[Seg, D, :, :][...], output=np.int32) labels[Seg, D, :, :] = temp offset_labels(D, Seg, labels, this_D_offset) this_D_offset += numregions total_regions += numregions condensed_count = condense_labels(D, numsegs, labels) print "Labeling depth %d: original %d, condensed %d" % (D, this_D_offset, condensed_count) for Seg in range (numsegs): offset_labels(D, Seg, labels, cross_D_offset) cross_D_offset += condensed_count # XXX - apply cross-D offset print "Labeling took", int(time.time() - st), "seconds, ", condense_labels.total_time, "in condensing" print cross_D_offset, "total labels", total_regions, "before condensing" if DEBUG: assert np.max(labels) == cross_D_offset
except Exception, e: pass condense_labels = timed(overlaps.condense_labels) lf = h5py.File(output_path + "_partial", "w") chunking = [1, 1, chunksize, chunksize] labels = lf.create_dataset( "seglabels", segmentations.shape, dtype=np.int32, chunks=tuple(chunking), compression="gzip" ) total_regions = 0 cross_D_offset = 0 for D in range(depth): this_D_offset = 0 for Seg in range(numsegs): temp, numregions = ndimage_label(segmentations[Seg, D, :, :][...], output=np.int32) labels[Seg, D, :, :] = temp offset_labels(D, Seg, labels, this_D_offset) this_D_offset += numregions total_regions += numregions condensed_count = condense_labels(D, numsegs, labels) print "Labeling depth %d: original %d, condensed %d" % (D, this_D_offset, condensed_count) for Seg in range(numsegs): offset_labels(D, Seg, labels, cross_D_offset) cross_D_offset += condensed_count # XXX - apply cross-D offset print "Labeling took", int(time.time() - st), "seconds, ", condense_labels.total_time, "in condensing" print cross_D_offset, "total labels", total_regions, "before condensing" if DEBUG: assert np.max(labels) == cross_D_offset