Unikaj list:
Niestety listy Redis nie są naprawdę dobrym wyborem w tej sytuacji. Miałem ten sam problem, kiedy zacząłem używać Redis, wydają się oczywistego wyboru;). Listy Redis są przydatne, jeśli używasz ich jako zestawu tylko do odczytu lub jeśli chcesz po prostu popchnąć i wypchnąć, ale nie do modyfikowania elementu na środku listy.
Możesz „zaktualizować” elementy na liście Redis, jeśli znasz indeks elementu, ale wymaga to usunięcie i wstaw ponownie , i musi to być indeks, którego określenie jest strasznie nieefektywne. Robi to poprzez iterację kolekcji, ponieważ nie ma natywnego sposobu na zrobienie tego, a to nie jest dobry pomysł. To jest fragment IndexOf
metoda RedisClientList<T>
.
public int IndexOf(T item)
{
//TODO: replace with native implementation when exists
var i = 0;
foreach (var existingItem in this)
{
if (Equals(existingItem, item)) return i;
i++;
}
return -1;
}
Aby uzupełnić kod, będzie to:
public void UpdatePizza(Pizza pizza)
{
using (var redisClient = new RedisClient(Host, Port))
{
IRedisTypedClient<Pizza> redis = redisClient.As<Pizza>();
IRedisList<Pizza> pizzas = redis.Lists["pizzas:live"];
var toUpdate = pizzas.First(x => x.Id == pizza.Id);
toUpdate.State = pizza.State;
// Update by removing & inserting (don't do it!)
var index = pizzas.IndexOf(toUpdate);
pizzas.Remove(index);
pizzas.Insert(index, toUpdate);
}
}
Ale to nie jest dobry sposób na poradzenie sobie z tym, jak powiedziałem. Pobiera listę innych obiektów pizzy, a następnie iteruje po nich, aż będzie pasować do indeksu. I dwie operacje do aktualizacji! :( W takiej sytuacji najlepiej unikać list.
Rozwiązanie:
Ponieważ próbujesz uzyskać dostęp do pizzy za pomocą jej identyfikatora, możesz utworzyć unikalny klucz pizzy dla każdego obiektu, co pozwoli ci uzyskać bezpośredni dostęp do pizzy. Więc możemy użyć:
pizzas:live:{Id}
Przykłady:
Utwórz pizzę
using (var redisClient = new RedisClient())
{
IRedisTypedClient<Pizza> redis = redisClient.As<Pizza>();
var pizzaKey = string.Format("pizzas:live:{0}", 123);
var pizza = new Pizza { Id = 123, Type = "Mushroom", State = "Cooking" };
redis.SetEntry(pizzaKey, pizza);
}
Zdobądź pizzę według identyfikatora
using (var redisClient = new RedisClient())
{
IRedisTypedClient<Pizza> redis = redisClient.As<Pizza>();
var pizzaKey = string.Format("pizzas:live:{0}", pizza.Id);
var pizza = redis.GetValue(pizzaKey);
}
Zaktualizuj pizzę według identyfikatora (Po prostu GET i SET)
using (var redisClient = new RedisClient())
{
IRedisTypedClient<Pizza> redis = redisClient.As<Pizza>();
var pizzaKey = string.Format("pizzas:live:{0}", pizza.Id);
var pizza = redis.GetValue(pizzaKey); // Get
pizza.State = "Delivery"; // Update
redis.SetEntry(pizzaKey, pizza); // Save
}
Przejdź do innej „listy” (może:kiedy pizza zmienia stan)
using (var redisClient = new RedisClient())
{
var pizzaKey = string.Format("pizzas:live:{0}", pizza.Id);
var deliveredKey = string.Format("pizzas:delivered:{0}", pizza.Id);
redisClient.RenameKey(pizzaKey, deliveredKey);
}
Usuń pizzę
using (var redisClient = new RedisClient())
{
var pizzaKey = string.Format("pizzas:live:{0}", pizza.Id);
redisClient.Remove(pizzaKey);
}
Wymień wszystkie pizze na żywo
using (var redisClient = new RedisClient())
{
var livePizzaKeys = redisClient.ScanAllKeys("pizzas:live:*").ToList();
List<Pizza> livePizzas = redisClient.GetValues<Pizza>(livePizzaKeys);
}
Mam nadzieję, że to pomoże.