public static PhpArray Slice(PhpArray array, int offset, int length, bool preserveKeys) { if (array == null) { PhpException.ArgumentNull("array"); return null; } // absolutizes range: PhpMath.AbsolutizeRange(ref offset, ref length, array.Count); var iterator = array.GetBaseEnumerator(); // moves iterator to the first item of the slice; // starts either from beginning or from the end (which one is more efficient): if (offset < array.Count - offset) { for (int i = -1; i < offset; i++) iterator.MoveNext(); } else { for (int i = array.Count; i > offset; i--) iterator.MovePrevious(); } // copies the slice: PhpArray result = new PhpArray(length); int ikey = 0; for (int i = 0; i < length; i++) { KeyValuePair<IntStringKey, object> entry = iterator.Current; // integer keys are reindexed if preserveKeys is false, string keys are not touched: if (entry.Key.IsString) { result.Add(entry.Key, entry.Value); } else { if (!preserveKeys) result.Add(ikey++, entry.Value); else result.Add(entry.Key, entry.Value); } iterator.MoveNext(); } result.InplaceCopyOnReturn = true; return result; }