修正完成日触板候选判定
This commit is contained in:
@@ -3543,14 +3543,44 @@ impl PlatformExprStrategy {
|
|||||||
let stock_volume_ma20 = rolling("volume", 20);
|
let stock_volume_ma20 = rolling("volume", 20);
|
||||||
let stock_volume_ma60 = rolling("volume", 60);
|
let stock_volume_ma60 = rolling("volume", 60);
|
||||||
let stock_volume_ma100 = rolling("volume", 100);
|
let stock_volume_ma100 = rolling("volume", 100);
|
||||||
let touched_upper_limit = !market.paused
|
let touched_upper_limit = if intraday_same_day_factor {
|
||||||
&& (market.is_at_upper_limit_price(market.close)
|
!market.paused
|
||||||
|| market.is_at_upper_limit_price(market.open)
|
&& (market.is_at_upper_limit_price(market.close)
|
||||||
|| market.is_at_upper_limit_price(market.day_open));
|
|| market.is_at_upper_limit_price(market.open)
|
||||||
let touched_lower_limit = !market.paused
|
|| market.is_at_upper_limit_price(market.day_open))
|
||||||
&& (market.is_at_lower_limit_price(market.close)
|
} else if let Some(value) = factor
|
||||||
|| market.is_at_lower_limit_price(market.open)
|
.extra_factors
|
||||||
|| market.is_at_lower_limit_price(market.day_open));
|
.get("touched_upper_limit")
|
||||||
|
.copied()
|
||||||
|
.filter(|value| value.is_finite())
|
||||||
|
{
|
||||||
|
value != 0.0
|
||||||
|
} else {
|
||||||
|
!feature_market.paused
|
||||||
|
&& (feature_market.is_at_upper_limit_price(feature_market.high)
|
||||||
|
|| feature_market.is_at_upper_limit_price(feature_market.close)
|
||||||
|
|| feature_market.is_at_upper_limit_price(feature_market.open)
|
||||||
|
|| feature_market.is_at_upper_limit_price(feature_market.day_open))
|
||||||
|
};
|
||||||
|
let touched_lower_limit = if intraday_same_day_factor {
|
||||||
|
!market.paused
|
||||||
|
&& (market.is_at_lower_limit_price(market.close)
|
||||||
|
|| market.is_at_lower_limit_price(market.open)
|
||||||
|
|| market.is_at_lower_limit_price(market.day_open))
|
||||||
|
} else if let Some(value) = factor
|
||||||
|
.extra_factors
|
||||||
|
.get("touched_lower_limit")
|
||||||
|
.copied()
|
||||||
|
.filter(|value| value.is_finite())
|
||||||
|
{
|
||||||
|
value != 0.0
|
||||||
|
} else {
|
||||||
|
!feature_market.paused
|
||||||
|
&& (feature_market.is_at_lower_limit_price(feature_market.low)
|
||||||
|
|| feature_market.is_at_lower_limit_price(feature_market.close)
|
||||||
|
|| feature_market.is_at_lower_limit_price(feature_market.open)
|
||||||
|
|| feature_market.is_at_lower_limit_price(feature_market.day_open))
|
||||||
|
};
|
||||||
let amount = if intraday_same_day_factor {
|
let amount = if intraday_same_day_factor {
|
||||||
f64::NAN
|
f64::NAN
|
||||||
} else {
|
} else {
|
||||||
@@ -15626,7 +15656,7 @@ mod tests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn platform_stock_state_uses_current_day_limit_status_for_buy_scale() {
|
fn platform_stock_state_uses_completed_day_high_and_low_for_limit_touch() {
|
||||||
let date = d(2025, 3, 14);
|
let date = d(2025, 3, 14);
|
||||||
let symbol = "603813.SH";
|
let symbol = "603813.SH";
|
||||||
let data = DataSet::from_components(
|
let data = DataSet::from_components(
|
||||||
@@ -15646,8 +15676,8 @@ mod tests {
|
|||||||
day_open: 14.82,
|
day_open: 14.82,
|
||||||
open: 14.82,
|
open: 14.82,
|
||||||
high: 15.98,
|
high: 15.98,
|
||||||
low: 14.80,
|
low: 13.08,
|
||||||
close: 15.98,
|
close: 15.00,
|
||||||
last_price: 15.05,
|
last_price: 15.05,
|
||||||
bid1: 15.04,
|
bid1: 15.04,
|
||||||
ask1: 15.05,
|
ask1: 15.05,
|
||||||
@@ -15720,6 +15750,7 @@ mod tests {
|
|||||||
.expect("stock state");
|
.expect("stock state");
|
||||||
|
|
||||||
assert!(stock.touched_upper_limit);
|
assert!(stock.touched_upper_limit);
|
||||||
|
assert!(stock.touched_lower_limit);
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
@@ -15860,7 +15891,7 @@ mod tests {
|
|||||||
assert_eq!(stock.last, 19.06);
|
assert_eq!(stock.last, 19.06);
|
||||||
assert_eq!(stock.market_cap, 8.0);
|
assert_eq!(stock.market_cap, 8.0);
|
||||||
assert_eq!(stock.market_cap_bn, 8.0);
|
assert_eq!(stock.market_cap_bn, 8.0);
|
||||||
assert!(!stock.touched_upper_limit);
|
assert!(stock.touched_upper_limit);
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
@@ -15883,7 +15914,7 @@ mod tests {
|
|||||||
timestamp: Some("2025-04-08 10:18:00".to_string()),
|
timestamp: Some("2025-04-08 10:18:00".to_string()),
|
||||||
day_open: 10.0,
|
day_open: 10.0,
|
||||||
open: 10.0,
|
open: 10.0,
|
||||||
high: 20.0,
|
high: 22.0,
|
||||||
low: 10.0,
|
low: 10.0,
|
||||||
close: 20.0,
|
close: 20.0,
|
||||||
last_price: 12.0,
|
last_price: 12.0,
|
||||||
@@ -15908,7 +15939,10 @@ mod tests {
|
|||||||
pe_ttm: 8.0,
|
pe_ttm: 8.0,
|
||||||
turnover_ratio: Some(1.0),
|
turnover_ratio: Some(1.0),
|
||||||
effective_turnover_ratio: Some(1.0),
|
effective_turnover_ratio: Some(1.0),
|
||||||
extra_factors: BTreeMap::from([("listed_days".to_string(), 263.0)]),
|
extra_factors: BTreeMap::from([
|
||||||
|
("listed_days".to_string(), 263.0),
|
||||||
|
("touched_upper_limit".to_string(), 1.0),
|
||||||
|
]),
|
||||||
}],
|
}],
|
||||||
vec![CandidateEligibility {
|
vec![CandidateEligibility {
|
||||||
date,
|
date,
|
||||||
@@ -15976,6 +16010,7 @@ mod tests {
|
|||||||
assert!(stock.high.is_nan());
|
assert!(stock.high.is_nan());
|
||||||
assert!(stock.low.is_nan());
|
assert!(stock.low.is_nan());
|
||||||
assert!(stock.volume.is_nan());
|
assert!(stock.volume.is_nan());
|
||||||
|
assert!(!stock.touched_upper_limit);
|
||||||
|
|
||||||
let day = strategy.day_state(&ctx, date).expect("day state");
|
let day = strategy.day_state(&ctx, date).expect("day state");
|
||||||
let (selected, _, _) = strategy
|
let (selected, _, _) = strategy
|
||||||
|
|||||||
Reference in New Issue
Block a user