Skip to content

Commit

Permalink
Make StarlarkList no longer inherit from AbstractList
Browse files Browse the repository at this point in the history
This gets rid of the `modCount` field and saves 4 bytes for each `StarlarkList` instance.

PiperOrigin-RevId: 554419923
Change-Id: Ifdc53d93ea92e8fc8a62872f32706b38a7ac06c0
  • Loading branch information
hvadehra authored and copybara-github committed Aug 7, 2023
1 parent d664fb7 commit ead0e42
Show file tree
Hide file tree
Showing 2 changed files with 89 additions and 17 deletions.
88 changes: 86 additions & 2 deletions src/main/java/net/starlark/java/eval/StarlarkList.java
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,15 @@

import com.google.common.collect.ImmutableList;
import com.google.common.collect.Iterables;
import java.util.AbstractList;
import java.util.AbstractCollection;
import java.util.Arrays;
import java.util.Collection;
import java.util.Iterator;
import java.util.List;
import java.util.ListIterator;
import java.util.NoSuchElementException;
import java.util.function.Supplier;
import javax.annotation.Nonnull;
import javax.annotation.Nullable;
import net.starlark.java.annot.Param;
import net.starlark.java.annot.ParamType;
Expand Down Expand Up @@ -70,7 +76,7 @@
+ "['a', 'b', 'c', 'd'][::2] # ['a', 'c']\n"
+ "['a', 'b', 'c', 'd'][3:0:-1] # ['d', 'c', 'b']</pre>"
+ "Lists are mutable, as in Python.")
public abstract class StarlarkList<E> extends AbstractList<E>
public abstract class StarlarkList<E> extends AbstractCollection<E>
implements Sequence<E>, StarlarkValue, Mutability.Freezable, Comparable<StarlarkList<?>> {

// It's always possible to overeat in small bites but we'll
Expand Down Expand Up @@ -205,6 +211,12 @@ public static <T> StarlarkList<T> concat(
return wrap(mutability, res);
}

@Nonnull
@Override
public Iterator<E> iterator() {
return new Itr();
}

@Override
public int compareTo(StarlarkList<?> that) {
return Sequence.compare(this, that);
Expand Down Expand Up @@ -446,4 +458,76 @@ public Object pop(Object i) throws EvalException {
public StarlarkList<E> unsafeOptimizeMemoryLayout() {
return this;
}

private class Itr implements Iterator<E> {
private int cursor = 0;

@Override
public boolean hasNext() {
return cursor != size();
}

@Override
public E next() {
try {
int i = cursor;
E next = get(i);
cursor = i + 1;
return next;
} catch (IndexOutOfBoundsException e) {
throw new NoSuchElementException();
}
}
}

// the following List methods are deliberately left unsupported for now, but could be implemented
// if the need ever arises

@Override
@Nonnull
public List<E> subList(int fromIndex, int toIndex) {
throw new UnsupportedOperationException();
}

@Override
@Nonnull
public ListIterator<E> listIterator() {
throw new UnsupportedOperationException();
}

@Override
@Nonnull
public ListIterator<E> listIterator(int index) {
throw new UnsupportedOperationException();
}

@Override
public int lastIndexOf(Object o) {
throw new UnsupportedOperationException();
}

@Override
public int indexOf(Object o) {
throw new UnsupportedOperationException();
}

@Override
public E set(int index, E element) {
throw new UnsupportedOperationException();
}

@Override
public void add(int index, E element) {
throw new UnsupportedOperationException();
}

@Override
public E remove(int index) {
throw new UnsupportedOperationException();
}

@Override
public boolean addAll(int index, @Nonnull Collection<? extends E> c) {
throw new UnsupportedOperationException();
}
}
18 changes: 3 additions & 15 deletions src/test/java/net/starlark/java/eval/StarlarkMutableTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,6 @@
import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import org.junit.Test;
import org.junit.runner.RunWith;
Expand All @@ -46,24 +45,13 @@ public void testListViewsCheckMutability() throws Exception {
() -> it.remove());
}
{
Iterator<?> it = list.listIterator();
it.next();
assertThrows(
UnsupportedOperationException.class,
() -> it.remove());
assertThrows(UnsupportedOperationException.class, list::listIterator);
}
{
Iterator<?> it = list.listIterator(1);
it.next();
assertThrows(
UnsupportedOperationException.class,
() -> it.remove());
assertThrows(UnsupportedOperationException.class, () -> list.listIterator(1));
}
{
List<Object> sublist = list.subList(1, 2);
assertThrows(
UnsupportedOperationException.class,
() -> sublist.set(0, 4));
assertThrows(UnsupportedOperationException.class, () -> list.subList(1, 2));
}
}

Expand Down

0 comments on commit ead0e42

Please sign in to comment.