//! # Learning Profile Example //! //! Demonstrates how to build and update learning profiles from execution //! history. //! //! ## What This Example Shows //! - Creating a `LearningProfile` for an agent //! - Recording execution data with timestamps //! - Computing task type expertise from historical data //! - Understanding recency bias weighting //! - Confidence scoring based on sample size //! //! ## Run //! ```bash //! cargo run --example 02-learning-profile -p vapora-agents //! ``` use chrono::{Duration, Utc}; use vapora_agents::{ExecutionData, LearningProfile, TaskTypeExpertise}; fn main() { println!("=== Learning Profile Example ===\n"); // Step 1: Create sample execution history let agent_id = "developer-alice".to_string(); let now = Utc::now(); // Simulate 30 days of execution history let executions: Vec = (0..30) .map(|i| ExecutionData { timestamp: now - Duration::days(i), duration_ms: 200 + (i as u64 * 5), success: i < 28, // 93% success rate (28/30 successes) }) .collect(); println!("Agent: {}", agent_id); println!("Historical executions: {} days", executions.len()); println!("Success rate: {:.1}%\n", (28.0 / 30.0) * 100.0); // Step 2: Create learning profile let mut profile = LearningProfile::new(agent_id); println!("Created learning profile\n"); // Step 3: Compute task type expertise let coding_expertise = TaskTypeExpertise::from_executions(executions.clone(), "coding"); println!("=== Task Type Expertise: Coding ==="); println!( "Success rate: {:.2}%", coding_expertise.success_rate * 100.0 ); println!("Average duration: {}ms", coding_expertise.avg_duration_ms); println!("Total executions: {}", coding_expertise.total_executions); println!("Confidence: {:.2}", coding_expertise.confidence); println!( "Recent success rate: {:.2}%", coding_expertise.recent_success_rate * 100.0 ); // Step 4: Demonstrate recency bias println!("\n=== Recency Bias Impact ==="); println!("Recent 7 days: weighted 3Ɨ higher"); println!("Days 8-30: weighted 1Ɨ normal"); let recent_success = (6.0 / 7.0) * 100.0; // Last 7 days all successful let older_success = (22.0 / 23.0) * 100.0; // Days 8-30 println!("Recent success rate (7d): {:.1}%", recent_success); println!("Older success rate (23d): {:.1}%", older_success); println!( "Weighted average: {:.1}%\n", coding_expertise.success_rate * 100.0 ); // Step 5: Add expertise to profile profile.set_task_type_expertise("coding".to_string(), coding_expertise.clone()); // Simulate another task type with lower expertise let test_executions: Vec = (0..20) .map(|i| ExecutionData { timestamp: now - Duration::days(i), duration_ms: 150 + (i as u64 * 3), success: i < 16, // 80% success rate (16/20) }) .collect(); let testing_expertise = TaskTypeExpertise::from_executions(test_executions, "testing"); profile.set_task_type_expertise("testing".to_string(), testing_expertise.clone()); println!("=== Overall Profile ==="); println!("Agent expertise levels:"); println!( " coding: {:.1}% (high)", coding_expertise.success_rate * 100.0 ); println!( " testing: {:.1}% (medium)", testing_expertise.success_rate * 100.0 ); // Step 6: Demonstrate confidence scaling println!("\n=== Confidence Scaling ==="); println!("Confidence increases with sample size:"); let sample_sizes = vec![5, 10, 20, 50, 100]; for size in sample_sizes { let confidence = ((size as f64 - 1.0) / (size as f64 + 9.0)).min(1.0); println!(" {} samples → confidence: {:.2}", size, confidence); } println!("\nāœ“ Learning profile created and ready for task assignment"); }