У меня была та же проблема. Это простая проблема, заключающаяся в том, что вы не указали правильный путь.
Щелкните правой кнопкой мыши по файлу .fxml
и выберите свойства (для тех, кто использует eclipse, не будет сильно отличаться для другой IDE), а затем скопируйте скопируйте местоположение, начиная с /packagename
до конца, и это должно решить проблему
Похоже, вы этого хотите.
Cow
будет принимать &str
или String
.
use std::borrow::Cow;
#[derive(Debug, Eq, Hash, PartialEq)]
struct Complex<'a> {
n: i32,
s: Cow<'a, str>,
}
impl<'a> Complex<'a> {
fn new<S: Into<Cow<'a, str>>>(n: i32, s: S) -> Self {
Complex {
n: n,
s: s.into(),
}
}
}
fn main() {
let mut m = std::collections::HashMap::<Complex, i32>::new();
m.insert(Complex::new(42, "foo"), 123);
assert_eq!(123, *m.get(&Complex::new(42, "foo")).unwrap());
}
Комментарий о параметрах жизни:
Если вам не нравится параметр lifetime, и вам нужно работать только с &'static str
или String
, тогда вы можете использовать Cow<'static, str>
и удалить другие параметры времени жизни из блока impl и определения структуры.
Вы можете следовать идеям, описанным в . Как реализовать HashMap с двумя ключами? . Вот ответ «заимствованный объект-объект», ответ на ваш случай:
Создайте признак, который мы можем использовать в качестве общей цели Borrow
:
trait Key {
fn to_key(&self) -> (i32, &str);
}
Реализовать HashMap
-приобретенные черты для объекта-объекта:
use std::hash::{Hash, Hasher};
impl<'a> Hash for Key + 'a {
fn hash<H: Hasher>(&self, state: &mut H) {
self.to_key().hash(state)
}
}
impl<'a> PartialEq for Key + 'a {
fn eq(&self, other: &Self) -> bool {
self.to_key() == other.to_key()
}
}
impl<'a> Eq for Key + 'a {}
Реализовать признак для нашего основного типа и любых типов вторичного поиска:
impl Key for Complex {
fn to_key(&self) -> (i32, &str) {
(self.n, &self.s)
}
}
impl<'a> Key for (i32, &'a str) {
fn to_key(&self) -> (i32, &str) {
(self.0, self.1)
}
}
Реализовать Borrow
для всех типов поиска, возвращающих наш объект-объект:
use std::borrow::Borrow;
impl<'a> Borrow<Key + 'a> for Complex {
fn borrow(&self) -> &(Key + 'a) {
self
}
}
impl<'a> Borrow<Key + 'a> for (i32, &'a str) {
fn borrow(&self) -> &(Key + 'a) {
self
}
}
Преобразовать объект-объект во время запроса:
assert_eq!(Some(&123), m.get((42, "foo").borrow() as &Key));
Важным «полученным» является то, что весь ваш первичный ключ и ваши вторичные ключи должны иметь хэш таким же образом. Это означает, что одни и те же значения должны идти в вычисление хэша в том же порядке и количестве.
Вы можете определить Hash
вручную, чтобы убедиться, что ваш основной и дополнительный ключи hash одинаковы!
Вот еще один пример, на этот раз с перечислением:
#[derive(Debug, PartialEq, Eq)]
enum ConfigKey {
Text(String),
Binary(Vec<u8>),
}
Мы создаем параллельное перечисление, состоящее только из ссылок, поэтому его легко создать. Важно, чтобы мы определяли одни и те же варианты и в том же порядке, что и первичное перечисление, чтобы они были хэшированы одинаково. Мы полагаемся на то, что хеш String
и &str
использует тот же алгоритм, что и Vec<T>
и &[T]
:
impl ConfigKey {
fn as_ref(&self) -> ConfigKeyRef {
match self {
ConfigKey::Text(t) => ConfigKeyRef::Text(t),
ConfigKey::Binary(b) => ConfigKeyRef::Binary(b),
}
}
}
#[derive(Hash, PartialEq, Eq)]
enum ConfigKeyRef<'a> {
Text(&'a str),
Binary(&'a [u8]),
}
Мы используем это новое перечисление как наш общий базовый тип ключа :
trait Key {
fn to_key(&self) -> ConfigKeyRef;
}
И реализуем нашу черту для наших первичных и вторичных ключей:
impl Key for ConfigKey {
fn to_key(&self) -> ConfigKeyRef {
self.as_ref()
}
}
impl<'a> Key for &'a str {
fn to_key(&self) -> ConfigKeyRef {
ConfigKeyRef::Text(self)
}
}
Complex
отображается в API моего контейнера, поэтому мне нужно убедиться, что я могу обременять тип с помощью параметра продолжительности жизни, не слишком мутируя мой интерфейс. Моя первоначальная реакция заключается в том, что функциональностьCow
для копирования на запись слишком тяжелая, потому что я никогда не делаю никакого копирования, но в некотором смысле я почти это, потому что иногда я использую экземпляры, а иногда я использую ссылки , После того как я закончу переваривать ваш ответ, я дам вам знать, как это работает. – Craig M. Brandenburg 8 April 2016 в 00:02str
. Тем не менее, мне очень нравится ваша идея, потому что это упростит код в другом месте, потому что новыйComplex
охватывает как случаи владения, так и заимствования - нет необходимости в уникальном типе для каждого случая. Одна вещь, которая меня интригует, заключается в том, что стандартная библиотека Rust не использовала путь использованияCow
вместо двух типов, чтобы покрывать случаи владения и заимствования дляPath
/PathBuf
et al. ИдеяCow
кажется более обобщенной, потому что она работает и для сложных типов. Это было сделано для эффективности во время выполнения? – Craig M. Brandenburg 8 April 2016 в 19:29