intervaltree icon indicating copy to clipboard operation
intervaltree copied to clipboard

'IntervalTree' object has no attribute 'merge_neighbors'

Open alexpreynolds opened this issue 3 years ago • 11 comments

I am attempting to call merge_neighbors() on an IntervalTree instance, but I am running into the following error:

% ../test.py
IntervalTree([Interval(50, 80, {'chrom': 'chr1', 'id': 'F'}), Interval(100, 120, {'chrom': 'chr1', 'id': 'D'}), Interval(100, 140, {'chrom': 'chr1', 'id': 'C'}), Interval(120, 200, {'chrom': 'chr1', 'id': 'A'}), Interval(199, 260, {'chrom': 'chr1', 'id': 'B'})])
None
Traceback (most recent call last):
  ...
  File "../test.py", line 44, in main
    mn_tree = tree.copy().merge_neighbors()
AttributeError: 'IntervalTree' object has no attribute 'merge_neighbors'

Here is the minimal reproducible example script test.py:

#!/usr/bin/env python

import sys
import io
import intervaltree

test_intervals_str = '''chr1	50	80	F
chr1	100	120	D
chr1	100	140	C
chr1	120	200	A
chr1	199	260	B
'''

def main():
    # build tree
    tree = intervaltree.IntervalTree()
    intervals = io.StringIO(test_intervals_str)
    for interval in intervals:
        (chrom, start, stop, id) = interval.rstrip().split('\t')
        tree[int(start):int(stop)] = { 'chrom' : chrom, 'id' : id }
    print(tree)
    mo_tree = tree.copy().merge_overlaps()
    print(mo_tree)
    mn_tree = tree.copy().merge_neighbors()
    print(mn_tree)

if __name__ == '__main__':
    main()

It looks like merged_neighbors is in the version I am using (v3.1.0):

https://github.com/chaimleib/intervaltree/blob/328d6db96596a0b7180dd3ad3fae4f6ff7301e01/intervaltree/intervaltree.py#L770-L776

Here is my install log:

% git clone https://github.com/chaimleib/intervaltree.git
% cd intervaltree 
% python ./setup.py install
!!!>>> This is a RELEASE version <<<!!!

Version: 3.1.0
running install
running bdist_egg
running egg_info
writing intervaltree.egg-info/PKG-INFO
writing dependency_links to intervaltree.egg-info/dependency_links.txt
writing requirements to intervaltree.egg-info/requires.txt
writing top-level names to intervaltree.egg-info/top_level.txt
reading manifest file 'intervaltree.egg-info/SOURCES.txt'
reading manifest template 'MANIFEST.in'
writing manifest file 'intervaltree.egg-info/SOURCES.txt'
installing library code to build/bdist.macosx-10.9-x86_64/egg
running install_lib
running build_py
creating build/bdist.macosx-10.9-x86_64/egg
creating build/bdist.macosx-10.9-x86_64/egg/intervaltree
copying build/lib/intervaltree/intervaltree.py -> build/bdist.macosx-10.9-x86_64/egg/intervaltree
copying build/lib/intervaltree/interval.py -> build/bdist.macosx-10.9-x86_64/egg/intervaltree
copying build/lib/intervaltree/__init__.py -> build/bdist.macosx-10.9-x86_64/egg/intervaltree
copying build/lib/intervaltree/node.py -> build/bdist.macosx-10.9-x86_64/egg/intervaltree
byte-compiling build/bdist.macosx-10.9-x86_64/egg/intervaltree/intervaltree.py to intervaltree.cpython-38.pyc
byte-compiling build/bdist.macosx-10.9-x86_64/egg/intervaltree/interval.py to interval.cpython-38.pyc
byte-compiling build/bdist.macosx-10.9-x86_64/egg/intervaltree/__init__.py to __init__.cpython-38.pyc
byte-compiling build/bdist.macosx-10.9-x86_64/egg/intervaltree/node.py to node.cpython-38.pyc
creating build/bdist.macosx-10.9-x86_64/egg/EGG-INFO
copying intervaltree.egg-info/PKG-INFO -> build/bdist.macosx-10.9-x86_64/egg/EGG-INFO
copying intervaltree.egg-info/SOURCES.txt -> build/bdist.macosx-10.9-x86_64/egg/EGG-INFO
copying intervaltree.egg-info/dependency_links.txt -> build/bdist.macosx-10.9-x86_64/egg/EGG-INFO
copying intervaltree.egg-info/requires.txt -> build/bdist.macosx-10.9-x86_64/egg/EGG-INFO
copying intervaltree.egg-info/top_level.txt -> build/bdist.macosx-10.9-x86_64/egg/EGG-INFO
copying intervaltree.egg-info/zip-safe -> build/bdist.macosx-10.9-x86_64/egg/EGG-INFO
creating 'dist/intervaltree-3.1.0-py3.8.egg' and adding 'build/bdist.macosx-10.9-x86_64/egg' to it
removing 'build/bdist.macosx-10.9-x86_64/egg' (and everything under it)
Processing intervaltree-3.1.0-py3.8.egg
Removing /Users/areynolds/miniconda3/lib/python3.8/site-packages/intervaltree-3.1.0-py3.8.egg
Copying intervaltree-3.1.0-py3.8.egg to /Users/areynolds/miniconda3/lib/python3.8/site-packages
intervaltree 3.1.0 is already the active version in easy-install.pth

Installed /Users/areynolds/miniconda3/lib/python3.8/site-packages/intervaltree-3.1.0-py3.8.egg
Processing dependencies for intervaltree==3.1.0
Searching for sortedcontainers==2.4.0
Best match: sortedcontainers 2.4.0
Adding sortedcontainers 2.4.0 to easy-install.pth file

Using /Users/areynolds/miniconda3/lib/python3.8/site-packages
Finished processing dependencies for intervaltree==3.1.0

Am I not using merge_neighbors correctly, or is there some other issue? Thanks!

alexpreynolds avatar May 21 '21 07:05 alexpreynolds

You have probably installed it wrong and used the released version rather than the current git master. Note that the currently released version does not include the merge_neighbors feature.

pcworld avatar Jun 11 '21 17:06 pcworld

See install log.

alexpreynolds avatar Jun 11 '21 17:06 alexpreynolds

See install log.

It's still possible that you run the script in a wrong environment and use an older package which is installed elsewhere. When running your script with intervaltree from git, it does not crash:

$ python3 test.py
IntervalTree([Interval(50, 80, {'chrom': 'chr1', 'id': 'F'}), Interval(100, 120, {'chrom': 'chr1', 'id': 'D'}), Interval(100, 140, {'chrom': 'chr1', 'id': 'C'}), Interval(120, 200, {'chrom': 'chr1', 'id': 'A'}), Interval(199, 260, {'chrom': 'chr1', 'id': 'B'})])
None
None

I don't think this is a bug in intervaltree.

pcworld avatar Jun 11 '21 17:06 pcworld

The install log shows that this is installed via the git distribution. I am installing into a clean virtual environment.

alexpreynolds avatar Jun 11 '21 17:06 alexpreynolds

The second output in your test run is not what I expect for overlapping intervals, but this is getting a bit afield from my question, in any case.

alexpreynolds avatar Jun 11 '21 17:06 alexpreynolds

The second output in your test run is not what I expect for overlapping intervals, but this is getting a bit afield from my question, in any case.

merge_neighbors() does not return anything, it modifies the original tree, that's why it returns None.

pcworld avatar Jun 11 '21 17:06 pcworld

Could we get a new release that includes merge_neighbors?

leifwalsh avatar Sep 13 '21 02:09 leifwalsh

Are there any plans to release a new version that includes merge_neighbors?

limjiayi avatar Oct 05 '21 05:10 limjiayi

great library! Very much need merge_neighbors method.. Any chance to make it working?

DmitryKey avatar Nov 02 '21 18:11 DmitryKey

~~> It looks like merged_neighbors is in the version I am using (v3.1.0):~~

~~@alexpreynolds: I believe merge_neighbors(...) was added in my pull request, #105. @chaimleib has not yet pushed the latest code to PyPI.~~

~~You could install from GitHub in the meanwhile.~~

Edit: Oops, I misread this thread.

afparsons avatar Mar 14 '22 15:03 afparsons

I would benefit from merge_neighbors being released as well

MatrixManAtYrService avatar Feb 23 '23 06:02 MatrixManAtYrService