ways.core package

Submodules

ways.core.check module

Comparison operators and other useful functions.

ways.core.check.force_itertype(obj, allow_outliers=False, itertype=None)[source]

Change the given object into an iterable object, if it isn’t one already.

Parameters:
  • obj (any) – The object(s) to wrap in a list iterable
  • allow_outliers (bool, optional) – If True, returns True if obj is string
  • itertype (callable) – Any iterable object that is callable, such as list, set, dict, etc.
Returns:

A list, containing objects if is_itertype is False

Return type:

list[obj]

ways.core.check.is_itertype(obj, allow_outliers=False, outlier_check=<function is_string_instance>)[source]

Check if the obj is iterable. Returns False if string by default.

Parameters:
  • obj (any) – The object to check for iterable methods
  • allow_outliers (bool, optional) – If True, returns True if obj is string
  • outlier_check (function, optional) – A function to use to check for ‘bad itertypes’. This function does nothing if allow_outliers is True. If nothing is provided, strings are checked and rejected.
Returns:

If the input obj is a proper iterable type.

Return type:

bool

ways.core.check.is_string_instance(obj)[source]

bool: If the object is a string instance.

ways.core.check.is_string_type(obj)[source]

bool: If the object is a string type.

ways.core.compat module

Python 2/3 compatibility classes and functions.

Yes, import six is awesome. This just covers whatever six doesn’t.

class ways.core.compat.DirMixIn[source]

Bases: object

‘Mix-in to make implementing __dir__ method in subclasses simpler.

In Python 2, you can’t call super() in __dir__. This mixin lets you do it.

Example

>>> class Something(object):
>>>     def __dir__(self):
>>>         return super(Something, self).__dir__()
>>> print(dir(Something()))  # Raises AttributeError
>>> class Something(DirMixIn, object):
>>>     def __dir__(self):
>>>         return super(Something, self).__dir__()
>>> print(dir(Something()))  # Works

That’s all there is to it.

ways.core.grouping module

Various functions for grouping sequences of integers.

ways.core.grouping.chunkwise_iter(seq, size=2)[source]

generator: Split the given sequence by size.

ways.core.grouping.filter_consecutive_items(obj)[source]

Remove all consecutive elements but keep duplicate items.

Parameters:obj (iterable) – The list (or iterable) to process
Returns:The ranges from the given list
Return type:list[int or tuple]
ways.core.grouping.get_difference(list1, list2)[source]

Get the elements of list1 that are not in list2.

Note

This is NOT a symmetric_difference

Warning

This function will cause you to lose list order of list1 and list2

Parameters:
  • list1 (list) – The list to get the intersection with
  • list2 (list) – The list to get the intersection against
Returns:

The combination of list1 and list2

Return type:

list

ways.core.grouping.get_ordered_intersection(seq1, seq2, memory_efficient=False)[source]

Get the elements that exist in both given sequences.

This code will preserve the order of the first sequence given.

Parameters:
  • seq1 (iterable) – The sequence to iterate. Also determines return order.
  • seq2 (iterable) – The second sequence to compare against the first
  • memory_efficient (bool, optional) – If you know that every element in both sequences are small in size, enable this option for a potential speed boost.
Returns:

The common elements of the two sequences

Return type:

iterable[any]

ways.core.grouping.group_into(seq, maximum)[source]

Break a sequence up in a specified number of groups.

Example

>>> seq = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
>>> maximum = 4
>>> group_into(seq=seq, maximum=maximum)
>>> [[1, 4, 7, 10], [2, 5, 8], [3, 6, 9]]
Parameters:
  • seq (iterable) – The sequence to split up
  • maximum (int) – The number of groups to make
Returns:

Group of the original iterable sequence object

Return type:

list[iterable]

ways.core.grouping.group_nth(seq, by)[source]

Split the sequence by the given number.

Example

>>> seq = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
>>> maximum = 4
>>> group_nth(seq=seq, by=by)
>>> [[1, 2, 3, 4], [5, 6, 7, 8], [9, 10]]

Note

The number of groups that will be made is (len(seq) // by) + 1

Parameters:
  • seq (iterable) – The sequence to split up into some groups
  • maximum (int) – The size of the groups that will be made from the original seqence
Returns:

A group of the original iterable sequence object

Return type:

list[iterable]

ways.core.grouping.grouper(obj)[source]

Group a list together by its items.

Slightly different result than ranges, in cases where outlier items lie between two ranges.

Example

>>> list(ranges([0, 1, 2, 3, 4, 7, 10, 12, 14, 16]))
>>> [xrange(0, 4, 1), xrange(10, 16, 2)]
Parameters:obj (iterable) – The list (or iterable) to process
Returns:The ranges from the given list
Return type:list[int or tuple]
ways.core.grouping.has_common_elements(*args)[source]

bool: Tests a variable number of sequences for common elements.

ways.core.grouping.pairwise(iterable)[source]

Change an iterable item in to pairs -> (s0,s1), (s1,s2), (s2, s3), …

ways.core.grouping.ranges(obj, return_range=True)[source]

Get the start and end ranges for a list of discontinuous int ranges.

Reference: http://stackoverflow.com/questions/39709606/

Example

>>> list(ranges([0, 1, 2, 3, 4  7, 10, 12, 14, 16]))
>>> [xrange(0, 4, 1), 7, xrange(10, 16, 2)]
Parameters:
  • obj (list[int]) – A list of integers to get the sequence of
  • return_range (bool) – If you just need an iterable and you don’t care about keeping the start/end/step, setting to True is more efficient on memory. If False, returns a tuple with start, end, and step.
Yields:

[int or range or tuple] – The ranges from the given list

ways.core.grouping.uniquify_list(seq, idfun=None)[source]

Order preserving way to get unique elements in a list.

This function is a bit dirty but extremely fast (see benchmark).

Reference: https://www.peterbe.com/plog/uniqifiers-benchmark

Parameters:
  • seq (list) – The list to make unique
  • idfun (func) – An optional function to run, as part of the uniquifier
Returns:

The uniquified list

Return type:

list

ways.core.loop module

For-loop helper methods.

ways.core.loop.last_iter(iterable)[source]

Wrap a loop to determine when the last value of a loop is found.

Reference:
https://stackoverflow.com/questions/1630320
Parameters:iterable (iterable) – The objects to move through
ways.core.loop.walk_items(obj)[source]

Iterate and yield parts of an object.

Example

>>> foo = ('fee', 'fi', 'fo', 'fum')
>>> print(list(walk_items(foo)))
>>> # Result: [('foo', ), ('foo', 'fi'), ('foo', 'fi', 'fo'),
>>> #          ('fee', 'fi', 'fo', 'fum')]

Note

This function requires the object use __len__, and __getitem__.

Parameters:obj (iterable) – Some object to return the parts of.
Yields:Parts of the object.

ways.core.pathrip module

Tools for dealing with file paths.

All of these functions should be OS-independent or at least indicate if not.

ways.core.pathrip.get_subfolder_root(path, subfolders, method='tail')[source]

Find the path of some path, using some consecutive subfolders.

Parameters:
  • path (str) – The path to get the root of.
  • subfolders (list[str] or str) – The folders to search for in the path.
  • method (callable[str, list[str]] or str, optional) – The strategy used to get the root subfolders. A function is acceptable or a preset string can be used. String options: ‘tail’: Search a path to get the longest possible match (the last tail).
Returns:

The root path that contains the subfolders.

Return type:

str

ways.core.pathrip.get_subfolder_root_tail(path, subfolders)[source]

Get the longest match of some path, using some subfolders.

Example

>>> root = '/jobs/rnd_ftrack/shots/sh01/maya/scenes/modeling/RELEASE/some_file_name.ma'
>>> subfolders = ['maya/scenes']
>>> get_subfolder_root_tail(root, subfolders)
'/jobs/rnd_ftrack/shots/sh01/maya/scenes'

Note

If a path has more than one match for subfolders, the last match is used.

Parameters:
  • path (str) – The path to get the root of.
  • subfolders (list[str] or str) – The folders to search for in the path.
Returns:

The path that matches some subfolder or an empty string.

Return type:

str

ways.core.pathrip.split_os_path_asunder(path)[source]

Split up a path, even if it is in Windows and has a letter drive.

Parameters:path (str) – The path to split up into parts.
Returns:The split path.
Return type:list[str]
ways.core.pathrip.split_path_asunder(path)[source]

Split a path up into individual folders.

This function is OS-independent but does not take into account Windows drive letters. For that, check out split_os_path_asunder.

Reference:
http://www.stackoverflow.com/questions/4579908.

Note

If this method is used on Windows paths, it’s recommended to os.path.splitdrive() before running this method on some path, to handle edge cases where driver letters have different meanings (example: c:path versus c:path)

Parameters:path (str) – The path to split up into parts.
Returns:The split path.
Return type:list[str]

ways.core.testsuite module

Discover and run the Python test files in this package.

ways.core.testsuite.discover_and_run()[source]

Look in the tests/test_*.py folder for unittests and run them all.

Module contents

High frequency modules, classes and functions to include in projects.