diff --git a/src/duckdb/extension/core_functions/aggregate/holistic/mode.cpp b/src/duckdb/extension/core_functions/aggregate/holistic/mode.cpp index dc09dd32f..24f5890cf 100644 --- a/src/duckdb/extension/core_functions/aggregate/holistic/mode.cpp +++ b/src/duckdb/extension/core_functions/aggregate/holistic/mode.cpp @@ -234,15 +234,12 @@ struct BaseModeFunction { } template - static void Combine(const STATE &source, STATE &target, AggregateInputData &) { + static void Combine(const STATE &source, STATE &target, AggregateInputData &aggr_input_data) { if (!source.frequency_map) { return; } if (!target.frequency_map) { - // Copy - don't destroy! Otherwise windowing will break. - target.frequency_map = new typename STATE::Counts(*source.frequency_map); - target.count = source.count; - return; + target.frequency_map = TYPE_OP::CreateEmpty(aggr_input_data.allocator); } for (auto &val : *source.frequency_map) { auto &i = (*target.frequency_map)[val.first]; diff --git a/src/duckdb/src/function/table/arrow.cpp b/src/duckdb/src/function/table/arrow.cpp index d41f63b2c..9747d16af 100644 --- a/src/duckdb/src/function/table/arrow.cpp +++ b/src/duckdb/src/function/table/arrow.cpp @@ -245,10 +245,10 @@ static bool CanPushdown(const ArrowType &type) { case LogicalTypeId::UBIGINT: case LogicalTypeId::FLOAT: case LogicalTypeId::DOUBLE: - case LogicalTypeId::VARCHAR: return true; + case LogicalTypeId::VARCHAR: case LogicalTypeId::BLOB: - // PyArrow doesn't support binary view filters yet + // PyArrow doesn't support binary and string view filters yet return type.GetTypeInfo().GetSizeType() != ArrowVariableSizeType::VIEW; case LogicalTypeId::DECIMAL: { switch (duck_type.InternalType()) { diff --git a/src/duckdb/src/function/table/version/pragma_version.cpp b/src/duckdb/src/function/table/version/pragma_version.cpp index 1e8ae5d8b..0e8af9cfa 100644 --- a/src/duckdb/src/function/table/version/pragma_version.cpp +++ b/src/duckdb/src/function/table/version/pragma_version.cpp @@ -1,5 +1,5 @@ #ifndef DUCKDB_PATCH_VERSION -#define DUCKDB_PATCH_VERSION "4-dev17" +#define DUCKDB_PATCH_VERSION "4-dev34" #endif #ifndef DUCKDB_MINOR_VERSION #define DUCKDB_MINOR_VERSION 4 @@ -8,10 +8,10 @@ #define DUCKDB_MAJOR_VERSION 1 #endif #ifndef DUCKDB_VERSION -#define DUCKDB_VERSION "v1.4.4-dev17" +#define DUCKDB_VERSION "v1.4.4-dev34" #endif #ifndef DUCKDB_SOURCE_ID -#define DUCKDB_SOURCE_ID "1c03ec0812" +#define DUCKDB_SOURCE_ID "6e4e3391db" #endif #include "duckdb/function/table/system_functions.hpp" #include "duckdb/main/database.hpp" diff --git a/src/duckdb/src/function/window/window_value_function.cpp b/src/duckdb/src/function/window/window_value_function.cpp index 0258b7d6b..5eaee1423 100644 --- a/src/duckdb/src/function/window/window_value_function.cpp +++ b/src/duckdb/src/function/window/window_value_function.cpp @@ -468,7 +468,11 @@ void WindowFirstValueExecutor::EvaluateInternal(ExecutionContext &context, DataC if (frame_width) { const auto first_idx = gvstate.value_tree->SelectNth(frames, 0); D_ASSERT(first_idx.second == 0); - cursor.CopyCell(0, first_idx.first, result, i); + if (first_idx.first < cursor.Count()) { + cursor.CopyCell(0, first_idx.first, result, i); + } else { + FlatVector::SetNull(result, i, true); + } } else { FlatVector::SetNull(result, i, true); } @@ -522,7 +526,7 @@ void WindowLastValueExecutor::EvaluateInternal(ExecutionContext &context, DataCh n -= last_idx.second; last_idx = gvstate.value_tree->SelectNth(frames, n); } - if (last_idx.second) { + if (last_idx.second || last_idx.first >= cursor.Count()) { // No last value - give up. FlatVector::SetNull(result, i, true); } else { @@ -592,7 +596,7 @@ void WindowNthValueExecutor::EvaluateInternal(ExecutionContext &context, DataChu if (n < frame_width) { const auto nth_index = gvstate.value_tree->SelectNth(frames, n - 1); - if (nth_index.second) { + if (nth_index.second || nth_index.first >= cursor.Count()) { // Past end of frame FlatVector::SetNull(result, i, true); } else { diff --git a/src/duckdb/src/include/duckdb/execution/merge_sort_tree.hpp b/src/duckdb/src/include/duckdb/execution/merge_sort_tree.hpp index 8c04ecde0..4461adf38 100644 --- a/src/duckdb/src/include/duckdb/execution/merge_sort_tree.hpp +++ b/src/duckdb/src/include/duckdb/execution/merge_sort_tree.hpp @@ -86,6 +86,8 @@ struct MergeSortTree { using RunElements = array; using Games = array; + static constexpr ElementType INVALID = std::numeric_limits::max(); + struct CompareElements { explicit CompareElements(const CMP &cmp) : cmp(cmp) { } @@ -122,6 +124,9 @@ struct MergeSortTree { pair SelectNth(const SubFrames &frames, idx_t n) const; inline ElementType NthElement(idx_t i) const { + if (tree.empty() || tree.front().first.empty()) { + return INVALID; + } return tree.front().first[i]; } diff --git a/src/duckdb/src/include/duckdb/function/window/window_collection.hpp b/src/duckdb/src/include/duckdb/function/window/window_collection.hpp index 95cf0534f..641eef78d 100644 --- a/src/duckdb/src/include/duckdb/function/window/window_collection.hpp +++ b/src/duckdb/src/include/duckdb/function/window/window_collection.hpp @@ -86,6 +86,10 @@ class WindowCursor { WindowCursor(const WindowCollection &paged, column_t col_idx); WindowCursor(const WindowCollection &paged, vector column_ids); + //! The row count of the paged collection + idx_t Count() const { + return paged.size(); + } //! Is the scan in range? inline bool RowIsVisible(idx_t row_idx) const { return (row_idx < state.next_row_index && state.current_row_index <= row_idx);