'Internal function (used from `_get_converter`) to apply
equivalence pairs.'

def _apply_equivalencies(self, unit, other, equivalencies):

    def make_converter(scale1, func, scale2):
        def convert(v):
            return (func((_condition_arg(v) / scale1)) * scale2)
        return convert
    for (funit, tunit, a, b) in equivalencies:
        if (tunit is None):
            try:
                ratio_in_funit = (other.decompose() / unit.decompose()).decompose([funit])
                return make_converter(ratio_in_funit.scale, a, 1.0)
            except UnitsError:
                pass
        else:
            try:
                scale1 = funit._to(unit)
                scale2 = tunit._to(other)
                return make_converter(scale1, a, scale2)
            except UnitsError:
                pass
            try:
                scale1 = tunit._to(unit)
                scale2 = funit._to(other)
                return make_converter(scale1, b, scale2)
            except UnitsError:
                pass
    def get_err_str(unit):
        unit_str = unit.to_string(u'unscaled')
        physical_type = unit.physical_type
        if (physical_type != u'unknown'):
            unit_str = u"'{0}'    ({1})".format(unit_str, physical_type)
        else:
            unit_str = u"'{0}'".format(unit_str)
        return unit_str
    unit_str = get_err_str(unit)
    other_str = get_err_str(other)
    raise UnitConversionError(u'{0}    and    {1}    are    not    convertible'.format(unit_str, other_str))
