如何高效检测连续数字中的n模式?含SQL、R语言及伪代码场景
Great question! Detecting repeating n-length patterns in sequential numbers is a common problem across data workflows, and the most efficient approach depends on your environment—SQL, raw vector processing, or R specifically. Let's break down each scenario with actionable methods:
For SQL tables, window functions are your best bet for efficiency, especially with large datasets. The key trick is to leverage row numbering to identify "shifted" values that signal repeating patterns.
Here's the core logic:
- Use
ROW_NUMBER()to assign a sequential index to each row in your ordered sequence. - Calculate the difference between your numeric value and the row number (
value - row_number()). For a repeating n-pattern, this difference will be identical across each occurrence of the pattern. - Group by this difference and the row number modulo n to isolate pattern segments, then count occurrences.
Example snippet (works in most SQL dialects like PostgreSQL, BigQuery):
WITH numbered_rows AS ( SELECT value, ROW_NUMBER() OVER (ORDER BY your_order_column) AS rn FROM your_table ), pattern_groups AS ( SELECT value, rn, value - rn AS group_id, MOD(rn - 1, n) AS pattern_position -- n is your target pattern length FROM numbered_rows ) SELECT STRING_AGG(value::TEXT, ',' ORDER BY pattern_position) AS pattern, COUNT(DISTINCT group_id) AS occurrence_count FROM pattern_groups GROUP BY group_id HAVING COUNT(DISTINCT group_id) >= 2; -- Filter for repeating patterns
For standalone vectors (e.g., in Python, R, or other languages), sliding windows combined with hashing is the most efficient approach, especially for large datasets:
- Generate all possible n-length sliding windows from the vector.
- Convert each window into a hashable key (like a string or tuple) to avoid expensive full-sequence comparisons.
- Use a hash map/dictionary to count how many times each key appears.
- Any key with a count ≥2 corresponds to a repeating n-pattern.
This method runs in O(m) time (where m is the length of the vector) if you use efficient hashing, making it scalable for large sequences.
In R, we can use packages like slider for clean sliding window handling, or implement a base R version for minimal dependencies. Below is a practical pseudo-code (and adaptable implementation) to detect repeating n-patterns:
Pseudo-Code & Explanation
detect_repeating_n_pattern <- function(input_vector, pattern_length) { # Guard clause: Not enough elements to have a repeating pattern if (length(input_vector) < 2 * pattern_length) { message("Vector is too short to contain a repeating n-pattern") return(list()) } # Generate all complete n-length sliding windows # Using slider::slide for simplicity (install with install.packages("slider")) library(slider) sliding_windows <- slide( input_vector, .f = identity, .before = pattern_length - 1, .complete = TRUE ) # Convert windows to hashable strings (since R can't hash vectors directly) window_keys <- sapply(sliding_windows, function(window) { paste(window, collapse = ",") }) # Count occurrences of each window pattern_counts <- table(window_keys) # Filter for patterns that appear at least twice repeated_patterns <- names(pattern_counts)[pattern_counts >= 2] # Convert string keys back to numeric vectors for readability result <- lapply(repeated_patterns, function(pattern_str) { as.numeric(strsplit(pattern_str, ",")[[1]]) }) return(result) }
Key Optimizations
- For very large vectors, replace the string conversion with a rolling hash (like the Rabin-Karp algorithm) to reduce memory usage—this avoids storing all windows explicitly.
- If you prefer base R, use
rollapplyfrom thezoopackage instead ofsliderfor sliding window generation.
内容的提问来源于stack exchange,提问作者Teletubbi-OS X

