Je veux permettre à l'utilisateur de rechercher des produits dans une fourchette de prix. L'utilisateur doit pouvoir utiliser n'importe quelle devise (USD, EUR, GBP, JPY, ...), quelle que soit la devise définie par le produit. Ainsi, le prix du produit est de 200 USD et, si l'utilisateur recherche les produits qui coûtent entre 100 et 200 EUR, il peut toujours le trouver. Comment le rendre rapide et efficace?
Voici ce que j'ai fait jusqu'à présent. Je stocke le price
, currency code
et calculated_price
c'est le prix en Euros (EUR) qui est la devise par défaut.
CREATE TABLE "products" (
"id" serial,
"price" numeric NOT NULL,
"currency" char(3),
"calculated_price" numeric NOT NULL,
CONSTRAINT "products_id_pkey" PRIMARY KEY ("id")
);
CREATE TABLE "currencies" (
"id" char(3) NOT NULL,
"modified" timestamp NOT NULL,
"is_default" boolean NOT NULL DEFAULT 'f',
"value" numeric NOT NULL, -- ratio additional to the default currency
CONSTRAINT "currencies_id_pkey" PRIMARY KEY ("id")
);
INSERT INTO "currencies" (id, modified, is_default, value)
VALUES
('EUR', '2012-05-17 11:38:45', 't', 1.0),
('USD', '2012-05-17 11:38:45', 'f', '1.2724'),
('GBP', '2012-05-17 11:38:45', 'f', '0.8005');
INSERT INTO "products" (price, currency, calculated_price)
SELECT 200.0 AS price, 'USD' AS currency, (200.0 / value) AS calculated_price
FROM "currencies" WHERE id = 'USD';
Si l' utilisateur est à la recherche d'une autre monnaie, disons USD, nous calculons le prix en euros et chercher la calculated_price
colonne.
SELECT * FROM "products" WHERE calculated_price > 100.0 AND calculated_price < 200.0;
De cette façon, nous pouvons comparer les prix très rapidement, car nous n'avons pas besoin de calculer le prix réel pour chaque ligne, car il est calculé une fois.
La mauvaise chose est qu'au moins chaque jour, nous devons recalculer le default_price
pour toutes les lignes, car les taux de change ont été modifiés.
Y a-t-il une meilleure façon de gérer cela?
N'y a-t-il pas d'autre solution intelligente? Peut-être une formule mathématique? J'ai une idée que calculated_price
c'est un ratio par rapport à une variable X
et, lorsque la devise change, nous ne mettons à jour que cette variable X
, pas la calculated_price
, donc nous n'avons même pas besoin de mettre à jour quoi que ce soit (lignes) ... Peut-être qu'un mathématicien peut le résoudre comme ça?
la source
calculated_price
à jour le tout? Je pourrais simplement stocker leinitial_currency_value
(taux de change constant qui est pris, disons, aujourd'hui) et toujours calculer par rapport à cela! Et lorsque vous affichez le prix en euros, calculez par rapport au taux de change réel, bien sûr. Ai-je raison? Ou il y a un problème que je ne vois pas?Je suis venu avec ma propre idée. Dites-moi si ça va vraiment marcher, s'il vous plaît!
Le problème.
Lorsque le produit est ajouté dans le
products
tableau, le prix est converti dans la devise par défaut (EUR) et stocké dans lacalculated_price
colonne.Nous voulons que cet utilisateur puisse rechercher (filtrer) les prix de n'importe quelle devise. Cela se fait en convertissant le prix d'entrée en devise par défaut (EUR) et en le comparant avec la
calculated_price
colonne.Nous devons mettre à jour les taux de change, afin que les utilisateurs puissent rechercher par nouveau taux de change. Mais le problème est - comment mettre à jour
calculated_price
efficacement.La solution (espérons-le).
Non! :)
L'idée est que nous prenons les taux de change d'hier ( tous de la même date ) en
calculated_price
utilisant uniquement ceux-ci. Comme ... pour toujours! Pas de mises à jour quotidiennes. La seule chose dont nous avons besoin avant de comparer / filtrer / rechercher les prix est de prendre les taux de change d'aujourd'hui comme ceux d'hier.Ainsi,
calculated_price
nous n'utiliserons que le taux de change de la date fixe (nous avons choisi, disons, hier). Nous aurons besoin de convertir le prix d'aujourd'hui en prix d'hier. En d'autres termes, prenez le taux du jour et convertissez-le en taux d'hier:Et voici le tableau des devises:
Voici comment ajouter un produit qui coûte 200 USD et comment le
calculated_price
get est calculé: du USD au plus récent taux EUR et au taux fixe (ancien)Cela peut également être pré-calculé du côté client et c'est ce que je vais faire - calculer le prix d'entrée de l'utilisateur à la
calculated_price
valeur compatible avant de faire une requête, donc il sera utilisé bon vieuxSELECT * FROM products WHERE calculated_price > 100.0 AND calculated_price < 200.0;
Conclusion.
Cette idée m'est venue il y a quelques heures à peine et actuellement je vous demande de vérifier si j'ai raison sur cette solution. Qu'est-ce que tu penses? Est-ce que ça va marcher? Ou je me suis trompé?
J'espère que vous comprenez tout cela. Je ne suis pas natif anglophone, il est également tard et je suis fatigué. :)
METTRE À JOUR
Eh bien, il semble qu'il résout un problème, mais en introduit un autre. Dommage. :)
la source
rate_newest / rate_fixed
est différent par devise, et cette solution ne prend en compte que celle de l'argent choisi par l'utilisateur dans la recherche. Tout prix dans une devise différente ne serait pas comparé à des taux à jour. La réponse que j'ai soumise avait en quelque sorte un problème similaire, mais je pense que je l'ai corrigé dans la version mise à jour.