Is there a workaround for ORA-01795: maximum number of expressions in a list is 1000 error?

前端 未结 11 788
忘掉有多难
忘掉有多难 2020-11-27 16:14

Is there a workaround for

\'ORA-01795: maximum number of expressions in a list is 1000 error\'

I have a query and it is selecting fields based

相关标签:
11条回答
  • 2020-11-27 17:04
        **Divide a list to lists of n size**
    
        import java.util.AbstractList;
        import java.util.ArrayList;
        import java.util.List;
    
        public final class PartitionUtil<T> extends AbstractList<List<T>> {
    
            private final List<T> list;
            private final int chunkSize;
    
            private PartitionUtil(List<T> list, int chunkSize) {
                this.list = new ArrayList<>(list);
                this.chunkSize = chunkSize;
            }
    
            public static <T> PartitionUtil<T> ofSize(List<T> list, int chunkSize) {
                return new PartitionUtil<>(list, chunkSize);
            }
    
            @Override
            public List<T> get(int index) {
                int start = index * chunkSize;
                int end = Math.min(start + chunkSize, list.size());
    
                if (start > end) {
                    throw new IndexOutOfBoundsException("Index " + index + " is out of the list range <0," + (size() - 1) + ">");
                }
    
                return new ArrayList<>(list.subList(start, end));
            }
    
            @Override
            public int size() {
                return (int) Math.ceil((double) list.size() / (double) chunkSize);
            }
        }
    
    
    
    
    
    Function call : 
                  List<List<String>> containerNumChunks = PartitionUtil.ofSize(list, 999)
    

    more details: https://e.printstacktrace.blog/divide-a-list-to-lists-of-n-size-in-Java-8/

    0 讨论(0)
  • 2020-11-27 17:06

    Just use multiple in-clauses to get around this:

    select field1, field2, field3 from table1 
    where  name in ('value1', 'value2', ..., 'value999') 
        or name in ('value1000', ..., 'value1999') 
        or ...;
    
    0 讨论(0)
  • 2020-11-27 17:06

    Please use an inner query inside of the in-clause:

    select col1, col2, col3... from table1
     where id in (select id from table2 where conditions...)
    
    0 讨论(0)
  • 2020-11-27 17:08

    One more way:

    CREATE OR REPLACE TYPE TYPE_TABLE_OF_VARCHAR2 AS TABLE OF VARCHAR(100);
    -- ...
    SELECT field1, field2, field3
      FROM table1
      WHERE name IN (
        SELECT * FROM table (SELECT CAST(? AS TYPE_TABLE_OF_VARCHAR2) FROM dual)
      );
    

    I don't consider it's optimal, but it works. The hint /*+ CARDINALITY(...) */ would be very useful because Oracle does not understand cardinality of the array passed and can't estimate optimal execution plan.

    As another alternative - batch insert into temporary table and using the last in subquery for IN predicate.

    0 讨论(0)
  • 2020-11-27 17:10

    I ran into this issue recently and figured out a cheeky way of doing it without stringing together additional IN clauses

    You could make use of Tuples

    SELECT field1, field2, field3
    FROM table1
    WHERE (1, name) IN ((1, value1), (1, value2), (1, value3),.....(1, value5000));
    

    Oracle does allow >1000 Tuples but not simple values. More on this here,

    https://community.oracle.com/message/3515498#3515498
    and
    https://community.oracle.com/thread/958612

    This is of course if you don't have the option of using a subquery inside IN to get the values you need from a temp table.

    0 讨论(0)
提交回复
热议问题