Repository: duckdb/duckdb (language: python)

Issue:
Seeing a single value changed after inserting ~1.5million row polars df to duckdb and then querying back out
### What happens?

When I write these 9 polars dataframes (saved as parquet files here: https://drive.google.com/drive/folders/18-xFUBLvPyux-erwETaATOV_fUpkLp4B?usp=sharing) to a duckdb table, I find that one single value from one single column is changed when I read the data back out.

### To Reproduce

First, download these 9 parquet files to your local machine: https://drive.google.com/drive/folders/18-xFUBLvPyux-erwETaATOV_fUpkLp4B?usp=sharing

Then, run the following code:
```
import duckdb
import polars as pl
import os
from datetime import date
from zipfile import ZipFile

### Constants
FILESDIR = "path_you_saved_downloaded_parquet_files_to" 
DAYS = range(1,10)
DUCKDB_FILE = os.path.join("path_you_saved_downloaded_parquet_files_to", "so_test.ddb")

### Read data from disk and write to duckdb
for day in DAYS:
    pldf = pl.read_parquet(os.path.join(FILESDIR, f"f{day}_masked.parquet"))
    with duckdb.connect(database=DUCKDB_FILE, read_only=False) as conn:
        if day == 1:
            conn.execute(f"CREATE OR REPLACE TABLE so_test AS SELECT * FROM pldf")
        else:
            conn.execute(f"INSERT INTO so_test SELECT * FROM pldf")        

### Verify that the data has changed by comparing a specific row from last df to its record in duckdb
PROBLEM_ROW = 1108956

print(pldf.slice(PROBLEM_ROW,1))  # hour=4.0
with duckdb.connect(database=DUCKDB_FILE, read_only=False) as conn:
    print(conn.execute(f"SELECT * from so_test WHERE (DAILY_FILE_ROW_ORDER = {PROBLEM_ROW}) and (DAILY_FILE_DATE = '2021-01-09')").pl())  # hour=3.0 now
```

Below is a screenshot of what I see when I run the code above. Note the rows are identical except `hour` has been changed from `4.0` to `3.0` (Also, I see `hour` for that row has been changed to `3.0` even if I read the result as a pandas `.df()`). 
<img width="834" alt="screenshot for duckdb issue" src="https://github.com/user-attachments/assets/ee217594-528c-49d3-861e-016758a19c02">


### OS:

Windows Server 2019 Datacenter, Version 10.0.17763 Build 17763 x64

### DuckDB Version:

1.1.0

### DuckDB Client:

python (python version 3.9.6)

### Hardware:

_No response_

### Full Name:

Max Epstein

### Affiliation:

Max Power Consulting, LLC

### What is the latest build you tested with? If possible, we recommend testing with the latest nightly build.

I have tested with a stable release

### Did you include all relevant data sets for reproducing the issue?

Yes

### Did you include all code required to reproduce the issue?

- [X] Yes, I have

### Did you include all relevant configuration (e.g., CPU architecture, Python version, Linux distribution) to reproduce the issue?

- [X] Yes, I have
Seeing a single value changed after inserting ~1.5million row polars df to duckdb and then querying back out
### What happens?

When I write these 9 polars dataframes (saved as parquet files here: https://drive.google.com/drive/folders/18-xFUBLvPyux-erwETaATOV_fUpkLp4B?usp=sharing) to a duckdb table, I find that one single value from one single column is changed when I read the data back out.

### To Reproduce

First, download these 9 parquet files to your local machine: https://drive.google.com/drive/folders/18-xFUBLvPyux-erwETaATOV_fUpkLp4B?usp=sharing

Then, run the following code:
```
import duckdb
import polars as pl
import os
from datetime import date
from zipfile import ZipFile

### Constants
FILESDIR = "path_you_saved_downloaded_parquet_files_to" 
DAYS = range(1,10)
DUCKDB_FILE = os.path.join("path_you_saved_downloaded_parquet_files_to", "so_test.ddb")

### Read data from disk and write to duckdb
for day in DAYS:
    pldf = pl.read_parquet(os.path.join(FILESDIR, f"f{day}_masked.parquet"))
    with duckdb.connect(database=DUCKDB_FILE, read_only=False) as conn:
        if day == 1:
            conn.execute(f"CREATE OR REPLACE TABLE so_test AS SELECT * FROM pldf")
        else:
            conn.execute(f"INSERT INTO so_test SELECT * FROM pldf")        

### Verify that the data has changed by comparing a specific row from last df to its record in duckdb
PROBLEM_ROW = 1108956

print(pldf.slice(PROBLEM_ROW,1))  # hour=4.0
with duckdb.connect(database=DUCKDB_FILE, read_only=False) as conn:
    print(conn.execute(f"SELECT * from so_test WHERE (DAILY_FILE_ROW_ORDER = {PROBLEM_ROW}) and (DAILY_FILE_DATE = '2021-01-09')").pl())  # hour=3.0 now
```

Below is a screenshot of what I see when I run the code above. Note the rows are identical except `hour` has been changed from `4.0` to `3.0` (Also, I see `hour` for that row has been changed to `3.0` even if I read the result as a pandas `.df()`). 
<img width="834" alt="screenshot for duckdb issue" src="https://github.com/user-attachments/assets/ee217594-528c-49d3-861e-016758a19c02">


### OS:

Windows Server 2019 Datacenter, Version 10.0.17763 Build 17763 x64

### DuckDB Version:

1.1.0

### DuckDB Client:

python (python version 3.9.6)

### Hardware:

_No response_

### Full Name:

Max Epstein

### Affiliation:

Max Power Consulting, LLC

### What is the latest build you tested with? If possible, we recommend testing with the latest nightly build.

I have tested with a stable release

### Did you include all relevant data sets for reproducing the issue?

Yes

### Did you include all code required to reproduce the issue?

- [X] Yes, I have

### Did you include all relevant configuration (e.g., CPU architecture, Python version, Linux distribution) to reproduce the issue?

- [X] Yes, I have


Discussion / hints:
I'll note one more fact here in case it's a helpful hint as to what's going on:

Many records leading up to row `1108956` had `hour`=`3.0`. And in my duckdb table, `hour` changes to being `4.0` at the next row `1108957`, one record after it should change to `4.0`...
I'll note one more fact here in case it's a helpful hint as to what's going on:

Many records leading up to row `1108956` had `hour`=`3.0`. And in my duckdb table, `hour` changes to being `4.0` at the next row `1108957`, one record after it should change to `4.0`...

Fix patch:
diff --git a/src/storage/compression/rle.cpp b/src/storage/compression/rle.cpp
index f845baad323a..61524cda8ac1 100644
--- a/src/storage/compression/rle.cpp
+++ b/src/storage/compression/rle.cpp
@@ -57,11 +57,14 @@ struct RLEState {
 			} else {
 				// the values are different
 				// issue the callback on the last value
-				Flush<OP>();
+				// edge case: if a value has exactly 2^16 repeated values, we can end up here with last_seen_count = 0
+				if (last_seen_count > 0) {
+					Flush<OP>();
+					seen_count++;
+				}
 
 				// increment the seen_count and put the new value into the RLE slot
 				last_value = data[idx];
-				seen_count++;
 				last_seen_count = 1;
 			}
 		} else {


Test patch:
diff --git a/test/sql/storage/compression/rle/rle_many_repeated.test_slow b/test/sql/storage/compression/rle/rle_many_repeated.test_slow
new file mode 100644
index 000000000000..dca8635d215d
--- /dev/null
+++ b/test/sql/storage/compression/rle/rle_many_repeated.test_slow
@@ -0,0 +1,25 @@
+# name: test/sql/storage/compression/rle/rle_many_repeated.test_slow
+# description: Test forcing RLE as the compression scheme
+# group: [rle]
+
+require vector_size 2048
+
+load __TEST_DIR__/rle_many_repeated.db
+
+statement ok
+PRAGMA force_compression = 'rle'
+
+statement ok
+CREATE TABLE test_rle (a BIGINT);
+
+statement ok
+INSERT INTO test_rle SELECT 3::BIGINT FROM range(0, 65535) UNION ALL SELECT 4::BIGINT FROM range(100000);
+
+statement ok
+CHECKPOINT
+
+query II
+SELECT a, COUNT(*) FROM test_rle GROUP BY ALL
+----
+3	65535
+4	100000