Initial Dever 0.0.1
This commit is contained in:
commit
81233d098c
1479 files changed
+163782
No files matched your search
@@ -0,0 +1,231 @@
|
||||
use std::hint::black_box;
|
||||
use std::time::Instant;
|
||||
|
||||
#[derive(Debug)]
|
||||
enum ReferenceFailure {
|
||||
Fault(Fault),
|
||||
Failed(String, Fault),
|
||||
}
|
||||
|
||||
fn state_reference(value: &STATE_TYPE) -> Result<i64, Fault> {
|
||||
Ok(match value {
|
||||
STATE_TYPE::Variant0 => 0,
|
||||
STATE_TYPE::Variant1(number) => *number,
|
||||
STATE_TYPE::Variant2(text) => text.chars().count() as i64,
|
||||
})
|
||||
}
|
||||
|
||||
fn nullable_reference(value: &Option<String>) -> Result<i64, Fault> {
|
||||
Ok(match value {
|
||||
None => -1,
|
||||
Some(text) if text == "zero" => 0,
|
||||
Some(text) => text.chars().count() as i64,
|
||||
})
|
||||
}
|
||||
|
||||
fn operation_reference(value: i64) -> Result<i64, ReferenceFailure> {
|
||||
if value >= 0 {
|
||||
Ok(value)
|
||||
} else {
|
||||
Err(ReferenceFailure::Failed(
|
||||
"negative".into(),
|
||||
&FaultInfo {
|
||||
message: "Result.Failed",
|
||||
source: "reference.dever",
|
||||
line: 1,
|
||||
column: 1,
|
||||
},
|
||||
))
|
||||
}
|
||||
}
|
||||
|
||||
fn propagate_reference(value: i64) -> Result<i64, ReferenceFailure> {
|
||||
Ok(operation_reference(value)?)
|
||||
}
|
||||
|
||||
fn capture_reference(value: i64) -> Result<RESULT_TYPE, Fault> {
|
||||
match propagate_reference(value) {
|
||||
Ok(number) => Ok(RESULT_TYPE::Variant0(number)),
|
||||
Err(ReferenceFailure::Failed(message, _origin)) => Ok(RESULT_TYPE::Variant1(message)),
|
||||
Err(ReferenceFailure::Fault(fault)) => Err(fault),
|
||||
}
|
||||
}
|
||||
|
||||
fn change_reference(value: &STATE_TYPE) -> Result<STATE_TYPE, Fault> {
|
||||
Ok(match value {
|
||||
STATE_TYPE::Variant2(text) => {
|
||||
let mut result = String::with_capacity(text.len() + "新".len());
|
||||
result.push_str(text);
|
||||
result.push_str("新");
|
||||
STATE_TYPE::Variant2(result)
|
||||
}
|
||||
_ => value.clone(),
|
||||
})
|
||||
}
|
||||
|
||||
fn score(value: RESULT_TYPE) -> usize {
|
||||
match value {
|
||||
RESULT_TYPE::Variant0(number) => number as usize,
|
||||
RESULT_TYPE::Variant1(message) => message.len(),
|
||||
}
|
||||
}
|
||||
|
||||
fn sample(
|
||||
name: &str,
|
||||
sample: usize,
|
||||
implementation: &str,
|
||||
count: usize,
|
||||
mut operation: impl FnMut(usize) -> usize,
|
||||
) {
|
||||
let start = Instant::now();
|
||||
let mut checksum = 0usize;
|
||||
for position in 0..count {
|
||||
checksum = checksum.wrapping_add(black_box(operation(black_box(position))));
|
||||
}
|
||||
println!(
|
||||
"{name},{sample},{implementation},{},{checksum}",
|
||||
start.elapsed().as_nanos()
|
||||
);
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let states = [
|
||||
STATE_TYPE::Variant0,
|
||||
STATE_TYPE::Variant1(42),
|
||||
STATE_TYPE::Variant2("雪山树林".repeat(16)),
|
||||
];
|
||||
let texts = [None, Some("zero".into()), Some("雪山树林".repeat(16))];
|
||||
for state in &states {
|
||||
assert_eq!(
|
||||
GENERATED_STATE(state).unwrap(),
|
||||
state_reference(state).unwrap()
|
||||
);
|
||||
assert_eq!(
|
||||
GENERATED_CHANGE(state).unwrap(),
|
||||
change_reference(state).unwrap()
|
||||
);
|
||||
}
|
||||
for text in &texts {
|
||||
assert_eq!(
|
||||
GENERATED_NULLABLE(text).unwrap(),
|
||||
nullable_reference(text).unwrap()
|
||||
);
|
||||
}
|
||||
for value in [i64::MIN, -1, 0, 1, i64::MAX] {
|
||||
assert_eq!(
|
||||
GENERATED_PROPAGATE(value).map_err(|_| ()),
|
||||
propagate_reference(value).map_err(|_| ())
|
||||
);
|
||||
assert_eq!(
|
||||
GENERATED_CAPTURE(value).unwrap(),
|
||||
capture_reference(value).unwrap()
|
||||
);
|
||||
}
|
||||
println!("case,sample,implementation,elapsed_ns,checksum");
|
||||
for iteration in 0..9 {
|
||||
for generated in if iteration % 2 == 0 {
|
||||
[true, false]
|
||||
} else {
|
||||
[false, true]
|
||||
} {
|
||||
let implementation = if generated { "dever" } else { "rust" };
|
||||
if generated {
|
||||
sample(
|
||||
"choice_payload",
|
||||
iteration,
|
||||
implementation,
|
||||
1_000_000,
|
||||
|position| GENERATED_STATE(black_box(&states[position % 3])).unwrap() as usize,
|
||||
);
|
||||
sample(
|
||||
"nullable_text",
|
||||
iteration,
|
||||
implementation,
|
||||
1_000_000,
|
||||
|position| {
|
||||
GENERATED_NULLABLE(black_box(&texts[position % 3])).unwrap() as usize
|
||||
},
|
||||
);
|
||||
sample(
|
||||
"default_failure",
|
||||
iteration,
|
||||
implementation,
|
||||
500_000,
|
||||
|position| {
|
||||
black_box(GENERATED_PROPAGATE((position % 8) as i64 - 1)).unwrap_or(7)
|
||||
as usize
|
||||
},
|
||||
);
|
||||
sample(
|
||||
"capture_failure",
|
||||
iteration,
|
||||
implementation,
|
||||
500_000,
|
||||
|position| {
|
||||
score(black_box(
|
||||
GENERATED_CAPTURE((position % 8) as i64 - 1).unwrap(),
|
||||
))
|
||||
},
|
||||
);
|
||||
sample(
|
||||
"choice_copy",
|
||||
iteration,
|
||||
implementation,
|
||||
300_000,
|
||||
|_| match black_box(GENERATED_CHANGE(black_box(&states[2])).unwrap()) {
|
||||
STATE_TYPE::Variant2(text) => text.len(),
|
||||
_ => unreachable!(),
|
||||
},
|
||||
);
|
||||
} else {
|
||||
sample(
|
||||
"choice_payload",
|
||||
iteration,
|
||||
implementation,
|
||||
1_000_000,
|
||||
|position| state_reference(black_box(&states[position % 3])).unwrap() as usize,
|
||||
);
|
||||
sample(
|
||||
"nullable_text",
|
||||
iteration,
|
||||
implementation,
|
||||
1_000_000,
|
||||
|position| {
|
||||
nullable_reference(black_box(&texts[position % 3])).unwrap() as usize
|
||||
},
|
||||
);
|
||||
sample(
|
||||
"default_failure",
|
||||
iteration,
|
||||
implementation,
|
||||
500_000,
|
||||
|position| {
|
||||
black_box(propagate_reference((position % 8) as i64 - 1)).unwrap_or(7)
|
||||
as usize
|
||||
},
|
||||
);
|
||||
sample(
|
||||
"capture_failure",
|
||||
iteration,
|
||||
implementation,
|
||||
500_000,
|
||||
|position| {
|
||||
score(black_box(
|
||||
capture_reference((position % 8) as i64 - 1).unwrap(),
|
||||
))
|
||||
},
|
||||
);
|
||||
sample(
|
||||
"choice_copy",
|
||||
iteration,
|
||||
implementation,
|
||||
300_000,
|
||||
|_| match black_box(change_reference(black_box(&states[2])).unwrap()) {
|
||||
STATE_TYPE::Variant2(text) => text.len(),
|
||||
_ => unreachable!(),
|
||||
},
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in new issue
Block a user