Skip to content

Latest commit

 

History

History
170 lines (146 loc) · 3.7 KB

02_zip.org

File metadata and controls

170 lines (146 loc) · 3.7 KB

Solutions for zip

@solomon

zip :: [a] -> [b] -> [(a, b)]
zip [] _ = []
zip _ [] = []
zip (x:xs) (y:ys) = (x, y) : zip xs ys
const zip = (a, b) => {
  if (a.length === 0 || b.length === 0) {
    return [];
  }
  const [x, ...xs] = a;
  const [y, ...ys] = b;
  return [[x,y]].concat(zip(xs,ys));
}
const zipWith = (f, a, b) => {
  if (a.length === 0 || b.length === 0) {
    return [];
  }
  const [x, ...xs] = a;
  const [y, ...ys] = b;
  return [f(x,y)].concat(zipWith(f, xs,ys));
}

const add = (a, b) => a+b;

zipWith(add, [1,2,3,4], [1,2,3,4])

@andrew

def zip(*args)
  results = []
  length = args.map{ |itr| itr.size }.min || 0
  length.times do |i|
      results.push(args.map{ |itr| itr[i] })
  end
  results
end
def zip(*args)
  results = Array.new( args.map{ |itr| itr.size }.min || 0 )
  results.each_with_index do |_, i|
      results[i] = args.map { |itr| itr[i] }
  end
end
function zip(first_itr) {
  if (first_itr === undefined) throw new Error("Must pass in at least one iterable");
  const results = [];
  const remaining = Array.from(arguments).slice(1);
  const length = Math.min(first_itr.length, ...remaining.map((itr) => itr.length))
  for(let i = 0; i < length; i++) {
    const sub_result = []
    sub_result.push(first_itr[i]);
    remaining.forEach((itr) => sub_result.push(itr[i]))
    results.push(sub_result);
  }
  return results
}

@sibiar600

const zip = (arr1, arr2) => {
  const zipped = [];
  const shorterArr = (arr1.length <= arr2.length) ? arr1 : arr2;
  while (shorterArr.length) {
    zipped.push([ arr1.shift(), arr2.shift() ]);
  }
  return zipped;
};

Handles more than 2 arrays:

const zip = function() {
  const arrs = [...arguments];
  if (!arrs.length) return [];
  const zipped = [];
  const shortestArr = arrs.reduce(
      (accumulator, currentValue) => (currentValue.length < accumulator.length) ? currentValue : accumulator
  );
  while (shortestArr.length) {
    zipped.push(arrs.map(arr => arr.shift()));
  }
  return zipped;
};

https://codepen.io/sibiar600/pen/PBMyjW?editors=0011

@jyamad

// basic zip as generator
// assumes all inputs are arrays
function* zip_gen(...arrs) {
	if (arrs.length === 0) return;
	const minlen = Math.min(...arrs.map(a => a.length));
	for (let i = 0; i < minlen; i++)
		yield arrs.map(a => a[i]);
}

// return results as array
function zip(...arrs) {
	return [...zip_gen(...arrs)]
}
// zip generator, takes any iterable
function* zip_iterables(...iterables) {
	if (iterables.length === 0) return;
	const iters = iterables.map(a => a[Symbol.iterator]());
	while (true) {
		const nexts = iters.map(a => a.next());
		const dones = nexts.map(a => a.done);
		if (dones.some(d => d === true))
			return;
		yield nexts.map(a => a.value)
	}
}
// zip n iterables
// looping by recursive tail call
function zip_ntc(...args) {
	function zip_iter(iters, acc) {
		if (iters.some(x => x.length === 0))
			return acc;

		const heads = iters.map(x => x[0]);
		const rests = iters.map(x => x.slice(1));
		return zip_iter(rests, [...acc, heads]);
	}

	if (args.length === 0) return [];
	return zip_iter(args, []);
}
def my_zip(*args):
    """full workalike for built-in zip"""
    iters = [iter(a) for a in args]
    while True:
        try:
            yield tuple([next(a) for a in iters])
        except StopIteration:
            return