debug: 添加时长转换和匹配的详细日志

## 添加的日志内容

### 1. 时长转换日志
在AI分类匹配和随机匹配方法中添加:
- 轨道片段ID和名称
- 原始时长(微秒)
- 转换后时长(秒)
- 目标分类信息

### 2. 时长匹配详细日志
在find_best_duration_match方法中添加:
- 目标时长和可选片段数量
- 每个片段的详细信息:
  * 片段ID和素材名称
  * 素材片段时长(秒)
  * 是否满足时长要求
  * 匹配评分
  * 分类信息
- 最终选择的片段信息

### 3. 时长要求检查日志
在MaterialSegment的方法中添加:
- meets_duration_requirement: 显示素材时长vs要求时长的比较
- duration_match_score: 显示详细的评分计算过程

## 目的
确认单位转换是否正确:
- 模板轨道片段时长:微秒
- 素材片段时长:秒
- 转换公式:微秒 / 1,000,000 = 秒

这些日志将帮助验证时长匹配逻辑的正确性。
This commit is contained in:
imeepos 2025-07-18 13:40:46 +08:00
parent 274926182c
commit c0ab039de9
2 changed files with 54 additions and 6 deletions

View File

@ -518,6 +518,13 @@ impl MaterialMatchingService {
// 计算目标时长(微秒转秒)- 修复单位转换 // 计算目标时长(微秒转秒)- 修复单位转换
let target_duration = track_segment.duration as f64 / 1_000_000.0; let target_duration = track_segment.duration as f64 / 1_000_000.0;
println!("🕐 时长转换日志 - AI分类匹配:");
println!(" 轨道片段ID: {}", track_segment.id);
println!(" 轨道片段名称: {}", track_segment.name);
println!(" 原始时长(微秒): {}", track_segment.duration);
println!(" 转换后时长(秒): {:.3}", target_duration);
println!(" 目标分类: {}", target_category);
// 过滤出匹配分类的片段 // 过滤出匹配分类的片段
let category_segments: Vec<_> = available_segments let category_segments: Vec<_> = available_segments
.iter() .iter()
@ -588,6 +595,12 @@ impl MaterialMatchingService {
// 计算目标时长(微秒转秒)- 修复单位转换 // 计算目标时长(微秒转秒)- 修复单位转换
let target_duration = track_segment.duration as f64 / 1_000_000.0; let target_duration = track_segment.duration as f64 / 1_000_000.0;
println!("🕐 时长转换日志 - 随机匹配:");
println!(" 轨道片段ID: {}", track_segment.id);
println!(" 轨道片段名称: {}", track_segment.name);
println!(" 原始时长(微秒): {}", track_segment.duration);
println!(" 转换后时长(秒): {:.3}", target_duration);
// 过滤出未使用的片段 // 过滤出未使用的片段
let unused_segments: Vec<_> = available_segments let unused_segments: Vec<_> = available_segments
.iter() .iter()
@ -643,16 +656,42 @@ impl MaterialMatchingService {
let mut best_match = None; let mut best_match = None;
let mut best_score = 0.0; let mut best_score = 0.0;
for (segment, category, material) in segments { println!("🔍 开始寻找最佳时长匹配:");
if segment.meets_duration_requirement(target_duration) { println!(" 目标时长(秒): {:.3}", target_duration);
let score = segment.duration_match_score(target_duration); println!(" 可选片段数量: {}", segments.len());
for (i, (segment, category, material)) in segments.iter().enumerate() {
let meets_requirement = segment.meets_duration_requirement(target_duration);
let score = segment.duration_match_score(target_duration);
println!(" 片段{}: {} ({})", i + 1, segment.id, material.name);
println!(" 素材片段时长(秒): {:.3}", segment.duration);
println!(" 满足时长要求: {}", meets_requirement);
println!(" 匹配评分: {:.3}", score);
println!(" 分类: {}", category);
if meets_requirement {
if score > best_score { if score > best_score {
best_score = score; best_score = score;
best_match = Some((*segment, *category, *material)); best_match = Some((*segment, *category, *material));
println!(" ✅ 新的最佳匹配!");
} }
} else {
println!(" ❌ 时长不足,跳过");
} }
} }
if let Some((best_segment, best_category, best_material)) = &best_match {
println!("🎯 最终选择:");
println!(" 片段ID: {}", best_segment.id);
println!(" 素材名称: {}", best_material.name);
println!(" 片段时长(秒): {:.3}", best_segment.duration);
println!(" 最佳评分: {:.3}", best_score);
println!(" 分类: {}", best_category);
} else {
println!("❌ 未找到满足时长要求的片段");
}
best_match best_match
} }

View File

@ -382,23 +382,32 @@ impl MaterialSegment {
/// 检查片段是否满足最小时长要求 /// 检查片段是否满足最小时长要求
pub fn meets_duration_requirement(&self, required_duration: f64) -> bool { pub fn meets_duration_requirement(&self, required_duration: f64) -> bool {
self.duration >= required_duration let meets = self.duration >= required_duration;
println!(" 📏 时长要求检查: 素材{:.3}s >= 要求{:.3}s = {}",
self.duration, required_duration, meets);
meets
} }
/// 计算与目标时长的匹配度越接近越好返回0.0-1.0 /// 计算与目标时长的匹配度越接近越好返回0.0-1.0
pub fn duration_match_score(&self, target_duration: f64) -> f64 { pub fn duration_match_score(&self, target_duration: f64) -> f64 {
if self.duration < target_duration { if self.duration < target_duration {
println!(" 📊 匹配评分: 素材{:.3}s < 目标{:.3}s时长不足 = 0.0",
self.duration, target_duration);
return 0.0; // 时长不足,不匹配 return 0.0; // 时长不足,不匹配
} }
// 计算匹配度:时长越接近目标时长,分数越高 // 计算匹配度:时长越接近目标时长,分数越高
let excess_ratio = (self.duration - target_duration) / target_duration; let excess_ratio = (self.duration - target_duration) / target_duration;
if excess_ratio <= 0.1 { let score = if excess_ratio <= 0.1 {
1.0 // 超出10%以内,完美匹配 1.0 // 超出10%以内,完美匹配
} else if excess_ratio <= 0.5 { } else if excess_ratio <= 0.5 {
0.8 - (excess_ratio - 0.1) * 2.0 // 超出10%-50%,线性递减 0.8 - (excess_ratio - 0.1) * 2.0 // 超出10%-50%,线性递减
} else { } else {
0.3 // 超出50%以上,低匹配度 0.3 // 超出50%以上,低匹配度
} };
println!(" 📊 匹配评分: 素材{:.3}s vs 目标{:.3}s超出比例{:.1}% = {:.3}",
self.duration, target_duration, excess_ratio * 100.0, score);
score
} }
} }