#rust #rust-cargo
#Ржавчина #rust-груз
Вопрос:
Допустим, у меня есть файл с некоторыми константами в нем. Этот файл, вероятно, поступает из другого сервиса и может отличаться для разных сценариев. Теперь я хочу выжать из своей программы все до последней капли производительности, хочу, чтобы компилятор выполнял как можно больше оптимизации, и я бы скомпилировал проект для каждого сценария отдельно, если это необходимо.
Есть ли способ взять файл во время компиляции, превратить его в код rust с помощью некоторой логики преобразования, например, сгенерировать некоторые константы и скомпилировать результат (все внутри инструментария rust, никакой другой генерации кода)?
Комментарии:
1. То, как вы это сделаете, во многом зависит от того, как выглядят эти константы. Это просто числа и массивы или что-то в этом роде?
2.
const fn
пользователи пока не могут получить доступ к файлам, но в конечном итоге могут. Если это возможно, вы могли бы написатьconst MY_CONST: MyType = get_value_from_file();
const get_value_from_file() { ... }
3. @Hadus, как вы сказали, «пока не удается получить доступ к файлам «. Является ли это частью повестки дня Rust в настоящее время?
4. @TristanStorch: Недавно было несколько разговоров по этому поводу, но ничего определенного, AFAICT.
Ответ №1:
Если вы запишете build.rs
файл в корень вашего ящика, он будет компилироваться и запускаться при каждой компиляции ящика.
Обычно он используется для создания привязок C и тому подобного, но ничто не мешает вам использовать его в своих целях.
Обычно это build.rs
создает исходный файл Rust где-то в выходном каталоге, считывая переменную OUT_DIR
среды:
fn main() {
println!("cargo:rerun-if-changed=build.rs");
println!("cargo:rerun-if-changed=data.txt");
let out_dir = std::env::var_os("OUT_DIR").unwrap();
let path = std::path::Path::new(amp;out_dir).join("test.rs");
std::fs::write(amp;path, "pub fn test() { todo!() }").unwrap();
}
Затем исходный код включается в ваш проект, обычно в его собственном модуле с:
mod test {
include!(concat!(env!("OUT_DIR"), "/test.rs"));
}
Комментарии:
1. Несмотря на то, что речь идет о генерации кода, это, по-видимому, лучшее, что можно сделать на данный момент. Не на 100% доволен, но что поделаешь. Примет этот ответ.
Ответ №2:
Вы могли бы просто сгенерировать исходные файлы rust, содержащие ваши константы.
Эти части могут быть на любом языке:
- Создайте данные, которые вы хотите использовать в качестве констант
- Сохраните их в исходных файлах rust в качестве констант, используя некоторые манипуляции со строками
В rust:
pub mod const_file
вpath/to/mod.rs
use path::to::const_file::MY_CONST;
cargo build
ваша программа rust
Пример для массива констант, который вы получаете из python:
array = [0, 10, 34]
const_file_str = f"pub const MY_CONST: [u16; 3] = {array};n"
with open("path/to/const_file.rs", "w") as rust_file:
rust_file.write(const_file_str)
Комментарии:
1. Мне пришлось сделать что-то подобное, чтобы преодолеть ограничение на оценку const. (инициализация const не может длиться вечно)
2. Как я писал в своем первоначальном вопросе, я хочу остаться в области инструментов rust и, в частности, избегать «другой генерации кода»
3. Другой ответ лучше, но вы могли бы выполнить первые два шага в
build.rs
файле.