@function __zip($args...) {
  @return __unzip($args);
}

// todo: see about reversed order
@function __zip-map($props, $values: ()) {
  $index: 1;
  $length: if($props, length($props), 0);
  $result: ();

  @if not __is-list-like($props) {
    @return ();
  }

  @if $length > 0 and not $values and not __is-list(nth($props, 1)) {
    $values: ();
  }

  @while $index <= $length {
    $key: nth($props, $index);

    @if ($values and length($values) > 0) {
      $result: __set($result, $key, nth($values, $index));
    } @else if ($key) {
      $result-key: nth($key, 1);
      $result-value: if(length($key) > 1, nth($key, 2), null);
      $result: __set($result, $result-key, $result-value);
    }

    $index: $index + 1;
  }

  @return $result;
}

/// Creates a list of grouped elements, the first of which contains the first
/// elements of the given lists, the second of which contains the second elements
/// of the given lists, and so on.
///
///
/// @access public
/// @group List
/// @param {List...} $lists... The lists to process.
/// @returns {List} Returns the new list of grouped elements.
/// @example scss
/// $foo: _zip(('fred', 'barney'), (30, 40), (true, false));
/// // => (('fred', 30, true), ('barney', 40, false))

@function _zip($args...) {
  @return call(get-function("__zip"), $args...);
}

/// Creates a map composed from lists of property names and values. Provide
/// either a single two dimensional list, e.g. `(($key1, $value1), ($key2, $value2))`
/// or two lists, one of property names and one of corresponding values.
///
///
/// @access public
/// @group List
/// @param {List} $props The property names.
/// @param {List} $values [()] The property values.
/// @returns {Map} Returns the new map.
/// @example scss
/// $foo: _zip-map(('fred', 'barney'), (30, 40));
/// // => ( 'fred': 30, 'barney': 40 )

@function _zip-map($args...) {
  @return call(get-function("__zip-map"), $args...);
}

/// @alias _zip-map

@function _object($args...) {
  @return call(get-function("__zip-map"), $args...);
}
