midstreamer_strange_loop/
lib.rs1use dashmap::DashMap;
13use midstreamer_attractor::{AttractorAnalyzer, PhasePoint};
14use midstreamer_neural_solver::TemporalNeuralSolver;
15use midstreamer_temporal_compare::TemporalComparator;
16use serde::{Deserialize, Serialize};
17use std::collections::HashMap;
18use std::sync::Arc;
19use thiserror::Error;
20
21#[derive(Debug, Error)]
23pub enum StrangeLoopError {
24 #[error("Max meta-depth exceeded: {0}")]
25 MaxDepthExceeded(usize),
26
27 #[error("Safety constraint violated: {0}")]
28 SafetyViolation(String),
29
30 #[error("Invalid modification: {0}")]
31 InvalidModification(String),
32
33 #[error("Meta-learning failed: {0}")]
34 MetaLearningFailed(String),
35}
36
37#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, Serialize, Deserialize)]
39pub struct MetaLevel(pub usize);
40
41impl MetaLevel {
42 pub fn base() -> Self {
43 MetaLevel(0)
44 }
45
46 pub fn next(&self) -> Self {
47 MetaLevel(self.0 + 1)
48 }
49
50 pub fn level(&self) -> usize {
51 self.0
52 }
53}
54
55#[derive(Debug, Clone, Serialize, Deserialize)]
57pub struct MetaKnowledge {
58 pub level: MetaLevel,
59 pub pattern: String,
60 pub confidence: f64,
61 pub applications: Vec<String>,
62 pub learned_at: u64,
63}
64
65impl MetaKnowledge {
66 pub fn new(level: MetaLevel, pattern: String, confidence: f64) -> Self {
67 Self {
68 level,
69 pattern,
70 confidence,
71 applications: Vec::new(),
72 learned_at: std::time::SystemTime::now()
73 .duration_since(std::time::UNIX_EPOCH)
74 .unwrap()
75 .as_millis() as u64,
76 }
77 }
78}
79
80#[derive(Debug, Clone, Serialize, Deserialize)]
82pub struct SafetyConstraint {
83 pub name: String,
84 pub formula: String, pub enforced: bool,
86}
87
88impl SafetyConstraint {
89 pub fn new(name: impl Into<String>, formula: impl Into<String>) -> Self {
90 Self {
91 name: name.into(),
92 formula: formula.into(),
93 enforced: true,
94 }
95 }
96
97 pub fn always_safe() -> Self {
98 Self::new("always_safe", "G(safe)")
99 }
100
101 pub fn eventually_terminates() -> Self {
102 Self::new("eventually_terminates", "F(done)")
103 }
104}
105
106#[derive(Debug, Clone, Serialize, Deserialize)]
108pub struct ModificationRule {
109 pub name: String,
110 pub trigger: String,
111 pub action: String,
112 pub safety_check: bool,
113}
114
115impl ModificationRule {
116 pub fn new(
117 name: impl Into<String>,
118 trigger: impl Into<String>,
119 action: impl Into<String>,
120 ) -> Self {
121 Self {
122 name: name.into(),
123 trigger: trigger.into(),
124 action: action.into(),
125 safety_check: true,
126 }
127 }
128}
129
130#[derive(Debug, Clone, Serialize, Deserialize)]
132pub struct MetaLearningSummary {
133 pub total_levels: usize,
134 pub total_knowledge: usize,
135 pub total_modifications: usize,
136 pub safety_violations: usize,
137 pub learning_iterations: u64,
138}
139
140#[derive(Debug, Clone)]
142pub struct StrangeLoopConfig {
143 pub max_meta_depth: usize,
144 pub enable_self_modification: bool,
145 pub max_modifications_per_cycle: usize,
146 pub safety_check_enabled: bool,
147}
148
149impl Default for StrangeLoopConfig {
150 fn default() -> Self {
151 Self {
152 max_meta_depth: 3,
153 enable_self_modification: false, max_modifications_per_cycle: 5,
155 safety_check_enabled: true,
156 }
157 }
158}
159
160pub struct StrangeLoop {
162 config: StrangeLoopConfig,
163 meta_knowledge: Arc<DashMap<MetaLevel, Vec<MetaKnowledge>>>,
164 safety_constraints: Vec<SafetyConstraint>,
165 modification_rules: Vec<ModificationRule>,
166 learning_iterations: Arc<DashMap<MetaLevel, u64>>,
167 modification_count: usize,
168 safety_violations: usize,
169
170 #[allow(dead_code)]
172 temporal_comparator: TemporalComparator<String>,
173 attractor_analyzer: AttractorAnalyzer,
174 #[allow(dead_code)]
175 temporal_solver: TemporalNeuralSolver,
176}
177
178impl StrangeLoop {
179 pub fn new(config: StrangeLoopConfig) -> Self {
181 Self {
182 config,
183 meta_knowledge: Arc::new(DashMap::new()),
184 safety_constraints: vec![
185 SafetyConstraint::always_safe(),
186 SafetyConstraint::eventually_terminates(),
187 ],
188 modification_rules: Vec::new(),
189 learning_iterations: Arc::new(DashMap::new()),
190 modification_count: 0,
191 safety_violations: 0,
192 temporal_comparator: TemporalComparator::new(1000, 10000),
193 attractor_analyzer: AttractorAnalyzer::new(3, 10000),
194 temporal_solver: TemporalNeuralSolver::default(),
195 }
196 }
197
198 pub fn learn_at_level(
200 &mut self,
201 level: MetaLevel,
202 data: &[String],
203 ) -> Result<Vec<MetaKnowledge>, StrangeLoopError> {
204 if level.level() > self.config.max_meta_depth {
205 return Err(StrangeLoopError::MaxDepthExceeded(level.level()));
206 }
207
208 self.learning_iterations
210 .entry(level)
211 .and_modify(|v| *v += 1)
212 .or_insert(1);
213
214 let patterns = self.extract_patterns(level, data)?;
216
217 self.meta_knowledge
219 .entry(level)
220 .or_default()
221 .extend(patterns.clone());
222
223 if level.level() < self.config.max_meta_depth {
225 self.meta_learn_from_level(level)?;
226 }
227
228 Ok(patterns)
229 }
230
231 fn meta_learn_from_level(&mut self, level: MetaLevel) -> Result<(), StrangeLoopError> {
233 let knowledge = if let Some(k) = self.meta_knowledge.get(&level) {
235 k.clone()
236 } else {
237 return Ok(()); };
239
240 let meta_patterns: Vec<String> = knowledge.iter().map(|k| k.pattern.clone()).collect();
242
243 let next_level = level.next();
245 let _meta_knowledge = self.learn_at_level(next_level, &meta_patterns)?;
246
247 Ok(())
248 }
249
250 fn extract_patterns(
252 &self,
253 level: MetaLevel,
254 data: &[String],
255 ) -> Result<Vec<MetaKnowledge>, StrangeLoopError> {
256 let mut patterns = Vec::new();
257
258 for i in 0..data.len() {
260 for j in i + 1..data.len() {
261 if data[i] == data[j] {
262 let pattern = MetaKnowledge::new(
264 level,
265 data[i].clone(),
266 0.8, );
268 patterns.push(pattern);
269 }
270 }
271 }
272
273 patterns.truncate(100);
275
276 Ok(patterns)
277 }
278
279 pub fn apply_modification(&mut self, rule: ModificationRule) -> Result<(), StrangeLoopError> {
281 if !self.config.enable_self_modification {
282 return Err(StrangeLoopError::InvalidModification(
283 "Self-modification is disabled".to_string(),
284 ));
285 }
286
287 if self.modification_count >= self.config.max_modifications_per_cycle {
288 return Err(StrangeLoopError::InvalidModification(
289 "Max modifications per cycle reached".to_string(),
290 ));
291 }
292
293 if rule.safety_check && self.config.safety_check_enabled {
295 self.check_safety_constraints()?;
296 }
297
298 self.modification_rules.push(rule);
300 self.modification_count += 1;
301
302 Ok(())
303 }
304
305 fn check_safety_constraints(&mut self) -> Result<(), StrangeLoopError> {
307 for constraint in &self.safety_constraints {
308 if constraint.enforced {
309 if constraint.formula.contains("safe") {
312 continue;
314 }
315 }
316 }
317
318 Ok(())
319 }
320
321 pub fn add_safety_constraint(&mut self, constraint: SafetyConstraint) {
323 self.safety_constraints.push(constraint);
324 }
325
326 pub fn get_knowledge_at_level(&self, level: MetaLevel) -> Vec<MetaKnowledge> {
328 self.meta_knowledge
329 .get(&level)
330 .map(|k| k.clone())
331 .unwrap_or_default()
332 }
333
334 pub fn get_all_knowledge(&self) -> HashMap<MetaLevel, Vec<MetaKnowledge>> {
336 let mut result = HashMap::new();
337 for entry in self.meta_knowledge.iter() {
338 result.insert(*entry.key(), entry.value().clone());
339 }
340 result
341 }
342
343 pub fn get_summary(&self) -> MetaLearningSummary {
345 let total_knowledge: usize = self
346 .meta_knowledge
347 .iter()
348 .map(|entry| entry.value().len())
349 .sum();
350
351 MetaLearningSummary {
352 total_levels: self.meta_knowledge.len(),
353 total_knowledge,
354 total_modifications: self.modification_count,
355 safety_violations: self.safety_violations,
356 learning_iterations: self
357 .learning_iterations
358 .iter()
359 .map(|entry| *entry.value())
360 .sum(),
361 }
362 }
363
364 pub fn reset(&mut self) {
366 self.meta_knowledge.clear();
367 self.learning_iterations.clear();
368 self.modification_rules.clear();
369 self.modification_count = 0;
370 self.safety_violations = 0;
371 }
372
373 pub fn analyze_behavior(
375 &mut self,
376 trajectory_data: Vec<Vec<f64>>,
377 ) -> Result<String, StrangeLoopError> {
378 for (i, point_data) in trajectory_data.iter().enumerate() {
379 let point = PhasePoint::new(point_data.clone(), i as u64);
380 self.attractor_analyzer
381 .add_point(point)
382 .map_err(|e| StrangeLoopError::MetaLearningFailed(e.to_string()))?;
383 }
384
385 let analysis = self
386 .attractor_analyzer
387 .analyze()
388 .map_err(|e| StrangeLoopError::MetaLearningFailed(e.to_string()))?;
389
390 Ok(format!("{:?}", analysis.attractor_type))
391 }
392}
393
394impl Default for StrangeLoop {
395 fn default() -> Self {
396 Self::new(StrangeLoopConfig::default())
397 }
398}
399
400pub trait MetaLearner {
402 fn learn(&mut self, data: &[String]) -> Result<Vec<MetaKnowledge>, StrangeLoopError>;
403 fn meta_level(&self) -> MetaLevel;
404}
405
406#[cfg(test)]
407mod tests {
408 use super::*;
409
410 #[test]
411 fn test_meta_level() {
412 let base = MetaLevel::base();
413 assert_eq!(base.level(), 0);
414
415 let next = base.next();
416 assert_eq!(next.level(), 1);
417 }
418
419 #[test]
420 fn test_strange_loop_creation() {
421 let config = StrangeLoopConfig::default();
422 let strange_loop = StrangeLoop::new(config);
423
424 assert_eq!(strange_loop.modification_count, 0);
425 assert_eq!(strange_loop.safety_violations, 0);
426 }
427
428 #[test]
429 fn test_learning_at_level() {
430 let mut strange_loop = StrangeLoop::default();
431
432 let data = vec![
433 "pattern1".to_string(),
434 "pattern2".to_string(),
435 "pattern1".to_string(),
436 ];
437
438 let result = strange_loop.learn_at_level(MetaLevel::base(), &data);
439 assert!(result.is_ok());
440
441 let knowledge = strange_loop.get_knowledge_at_level(MetaLevel::base());
442 assert!(!knowledge.is_empty());
443 }
444
445 #[test]
446 fn test_max_depth_exceeded() {
447 let mut strange_loop = StrangeLoop::default();
448
449 let data = vec!["test".to_string()];
450 let deep_level = MetaLevel(10); let result = strange_loop.learn_at_level(deep_level, &data);
453 assert!(result.is_err());
454 }
455
456 #[test]
457 fn test_safety_constraint() {
458 let constraint = SafetyConstraint::always_safe();
459 assert_eq!(constraint.name, "always_safe");
460 assert!(constraint.enforced);
461 }
462
463 #[test]
464 fn test_modification_disabled() {
465 let mut strange_loop = StrangeLoop::default();
466
467 let rule = ModificationRule::new("test_rule", "trigger", "action");
468 let result = strange_loop.apply_modification(rule);
469
470 assert!(result.is_err()); }
472
473 #[test]
474 fn test_summary() {
475 let mut strange_loop = StrangeLoop::default();
476
477 let data = vec!["pattern1".to_string(), "pattern2".to_string()];
478 let _ = strange_loop.learn_at_level(MetaLevel::base(), &data);
479
480 let summary = strange_loop.get_summary();
481 assert!(summary.total_knowledge > 0);
482 assert_eq!(summary.safety_violations, 0);
483 }
484
485 #[test]
486 fn test_reset() {
487 let mut strange_loop = StrangeLoop::default();
488
489 let data = vec!["pattern1".to_string()];
490 let _ = strange_loop.learn_at_level(MetaLevel::base(), &data);
491
492 strange_loop.reset();
493
494 let summary = strange_loop.get_summary();
495 assert_eq!(summary.total_knowledge, 0);
496 assert_eq!(summary.total_modifications, 0);
497 }
498}