diff --git a/Cargo.lock b/Cargo.lock index 85bba23..d4c511d 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -41,6 +41,15 @@ dependencies = [ "memchr", ] +[[package]] +name = "alloca" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e5a7d05ea6aea7e9e64d25b9156ba2fee3fdd659e34e41063cd2fc7cd020d7f4" +dependencies = [ + "cc", +] + [[package]] name = "alsa" version = "0.11.0" @@ -814,25 +823,24 @@ dependencies = [ [[package]] name = "criterion" -version = "0.5.1" +version = "0.8.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f2b12d017a929603d80db1831cd3a24082f8137ce19c69e6447f54f5fc8d692f" +checksum = "950046b2aa2492f9a536f5f4f9a3de7b9e2476e575e05bd6c333371add4d98f3" dependencies = [ + "alloca", "anes", "cast", "ciborium", "clap", "criterion-plot", - "is-terminal", "itertools", "num-traits", - "once_cell", "oorandom", + "page_size", "plotters", "rayon", "regex", "serde", - "serde_derive", "serde_json", "tinytemplate", "walkdir", @@ -840,9 +848,9 @@ dependencies = [ [[package]] name = "criterion-plot" -version = "0.5.0" +version = "0.8.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6b50826342786a51a89e2da3a28f1c32b06e387201bc2d19791f622c673706b1" +checksum = "d8d80a2f4f5b554395e47b5d8305bc3d27813bacb73493eb1001e8f76dae29ea" dependencies = [ "cast", "itertools", @@ -1555,12 +1563,21 @@ dependencies = [ ] [[package]] -name = "hashlink" -version = "0.11.0" +name = "hashbrown" +version = "0.17.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ea0b22561a9c04a7cb1a302c013e0259cd3b4bb619f145b32f72b8b4bcbed230" +checksum = "ed5909b6e89a2db4456e54cd5f673791d7eca6732202bbf2a9cc504fe2f9b84a" dependencies = [ - "hashbrown 0.16.1", + "foldhash 0.2.0", +] + +[[package]] +name = "hashlink" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "32069d97bb81e38fa67eab65e3393bf804bb85969f2bc06bf13f64aef5aba248" +dependencies = [ + "hashbrown 0.17.1", ] [[package]] @@ -1581,12 +1598,6 @@ version = "0.4.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7f24254aa9a54b5c858eaee2f5bccdb46aaf0e486a595ed5fd8f86ba55232a70" -[[package]] -name = "hex-literal" -version = "1.1.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e712f64ec3850b98572bffac52e2c6f282b29fe6c5fa6d42334b30be438d95c1" - [[package]] name = "hexf-parse" version = "0.2.1" @@ -2064,22 +2075,11 @@ dependencies = [ "serde", ] -[[package]] -name = "is-terminal" -version = "0.4.17" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3640c1c38b8e4e43584d8df18be5fc6b0aa314ce6ebf51b53313d4306cca8e46" -dependencies = [ - "hermit-abi", - "libc", - "windows-sys 0.61.2", -] - [[package]] name = "itertools" -version = "0.10.5" +version = "0.13.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b0fd2260e829bddf4cb6ea802289de2f86d6a7a690192fbe91b3f46e0f2c8473" +checksum = "413ee7dfc52ee1a4949ceeb7dbc8a33f2d6c088194d9f922fb8318faf1f01186" dependencies = [ "either", ] @@ -2098,10 +2098,8 @@ dependencies = [ "criterion", "dirs", "hex", - "hex-literal", "iced", "rand", - "rayon", "reqwest", "rhai", "rodio", @@ -2229,10 +2227,11 @@ dependencies = [ [[package]] name = "libsqlite3-sys" -version = "0.37.0" +version = "0.38.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b1f111c8c41e7c61a49cd34e44c7619462967221a6443b0ec299e0ac30cfb9b1" +checksum = "f6c19a05435c21ac299d71b6a9c13db3e3f47c520517d58990a462a1397a61db" dependencies = [ + "cc", "pkg-config", "vcpkg", ] @@ -3074,6 +3073,16 @@ dependencies = [ "ttf-parser", ] +[[package]] +name = "page_size" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "30d5b2194ed13191c1999ae0704b7839fb18384fa22e49b57eeaa97d79ce40da" +dependencies = [ + "libc", + "winapi", +] + [[package]] name = "parking" version = "2.2.1" @@ -3569,9 +3578,9 @@ checksum = "7204ed6420f698836b76d4d5c2ec5dec7585fd5c3a788fd1cde855d1de598239" [[package]] name = "rusqlite" -version = "0.39.0" +version = "0.40.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a0d2b0146dd9661bf67bb107c0bb2a55064d556eeb3fc314151b957f313bcd4e" +checksum = "11438310b19e3109b6446c33d1ed5e889428cf2e278407bc7896bc4aaea43323" dependencies = [ "bitflags 2.10.0", "chrono", diff --git a/Cargo.toml b/Cargo.toml index e7a44b3..552253b 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -11,18 +11,16 @@ serde = { version = "1.0.228", features = ["derive"] } serde_json = "1.0.149" rhai = "1.24.0" chrono = "0.4.44" -rusqlite = { version = "0.39.0", features = ["chrono"] } +rusqlite = { version = "0.40.1", features = ["chrono", "bundled"] } reqwest = { version = "0", features = ["json", "stream", "multipart"] } rodio = "0.22.2" sha2 = "0.11.0" tokio = { version = "1.50.0", features = ["rt", "rt-multi-thread", "macros"] } -rayon = "1.12.0" hex = "0.4.3" -hex-literal = "1.1.0" zstd = "0.13.3" [dev-dependencies] -criterion = "0.5" +criterion = "0.8.2" [[bench]] name = "split_bench" # Имя файла в benches/ без расширения diff --git a/src/data_provider/card_stats.rs b/src/data_provider/card_stats.rs index 2374c0f..179db16 100644 --- a/src/data_provider/card_stats.rs +++ b/src/data_provider/card_stats.rs @@ -1,6 +1,7 @@ use crate::lang::CardStatistics; use crate::repetitions::CardSetSettings; use rusqlite::Connection; +use std::time::Instant; pub fn load_stats_of_set(set: &CardSetSettings, connection: &Connection) -> Vec { let mut stmt = connection.prepare("SELECT id, word_id, score, last_opened FROM card_stats WHERE set_id = ?1").unwrap(); @@ -22,7 +23,37 @@ pub fn load_stats_of_set(set: &CardSetSettings, connection: &Connection) -> Vec< buffer } + +pub fn add_stat_list(stat: &mut Vec, connection: &Connection) { + let inserting = stat.iter().map(|stat| format!("({}, {}, {}, {})", stat.word_id.to_string(), stat.set_id.to_string(), stat.score.to_string(), stat.last_open.timestamp().to_string())).collect::>().join(", "); + let query = format!("INSERT INTO card_stats (word_id, set_id, score, last_opened) VALUES {}", inserting); + let count = connection + .execute( + query.as_str(), + ( + ), + ); + + if count.is_err() { + println!("{}", count.unwrap_err()); + return; + } + + let last_index : u32 = connection.query_one("SELECT seq from sqlite_sequence WHERE name == ?1", ("card_stats".to_string(),), |row| row.get(0)).unwrap(); + + let start_index = last_index - (count.unwrap() as u32) + 1; + + let mut index = 0; + for id in start_index..=last_index { + stat[index].id = id as u32; + index += 1; + } + +} + + pub fn add_stat(stat: &mut CardStatistics, connection: &Connection) { + let time = Instant::now(); let index = connection .query_row( "INSERT INTO card_stats (word_id, set_id, score, last_opened) VALUES (?1, ?2, ?3, ?4) RETURNING id", @@ -37,9 +68,12 @@ pub fn add_stat(stat: &mut CardStatistics, connection: &Connection) { .unwrap_or_else(|e| {println!("{}", e); 0}); stat.id = index; + println!("Added stat: {}", time.elapsed().as_millis()); } pub fn update_stat_score(stat: &CardStatistics, connection: &Connection){ + let time = Instant::now(); + connection .execute( "UPDATE card_stats SET score = ?1, last_opened = ?2 WHERE id = ?3", @@ -50,6 +84,8 @@ pub fn update_stat_score(stat: &CardStatistics, connection: &Connection){ ), ) .unwrap_or_else(|e| {println!("{}", e); 0}); + println!("Updated stat: {}", time.elapsed().as_millis()); + } pub fn delete_stat(stat: &CardStatistics, connection: &Connection) { diff --git a/src/dictionary.rs b/src/dictionary.rs index a826202..c45ffad 100644 --- a/src/dictionary.rs +++ b/src/dictionary.rs @@ -326,6 +326,7 @@ impl DictionaryState { if !self.search.is_empty() { if word.key.contains(&self.search) == false && word.value.contains(&self.search) == false + && word.tags.contains(&self.search) == false { continue; } diff --git a/src/lang.rs b/src/lang.rs index 7a0e296..b9734c6 100644 --- a/src/lang.rs +++ b/src/lang.rs @@ -1,6 +1,5 @@ -use crate::data_provider::card_stats::{ - add_stat, delete_stat, load_stats_of_set, update_stat_score, -}; +use crate::data_provider::card_stats::{add_stat_list, delete_stat, load_stats_of_set, update_stat_score}; +use crate::data_provider::history::{push_note, HistoryItem}; use crate::repetitions::CardSetSettings; use crate::AppState; use chrono::{DateTime, Utc}; @@ -13,7 +12,7 @@ use serde::{Deserialize, Serialize}; use std::cmp::min; use std::collections::HashMap; use std::sync::{Arc, Mutex}; -use crate::data_provider::history::{push_note, HistoryItem}; +use std::time::Instant; const MAX_HISTORY_LEN: usize = 20; const MAX_HISTORY_LEN_PART: f32 = 0.33; @@ -329,7 +328,7 @@ impl CardSet { let saved_ids = current_set.iter().map(|l| l.word_id).collect::>(); let word_ids = last_list.iter().map(|l| l.id).collect::>(); - last_list + let new_stats: &mut Vec = &mut last_list .iter() .filter(|word| !saved_ids.contains(&word.id)) .map(|word| CardStatistics { @@ -338,12 +337,16 @@ impl CardSet { last_open: Utc::now(), score: 1, set_id: settings.id.clone(), - }) - .for_each(|mut new_statistic| { - add_stat(&mut new_statistic, &state_locked.connection); - current_set.push(new_statistic); - }); + }).collect(); + let time = Instant::now(); + + if !new_stats.is_empty() { + add_stat_list(new_stats, &state_locked.connection); + current_set.append(new_stats); + } + + println!("Added {} stats: {}", new_stats.len(), time.elapsed().as_millis()); let mut index = 0; for stat in current_set.clone() { if !word_ids.contains(&stat.word_id) {