简体   繁体   中英

Design and store a Currency Exchange Rates Cross Table

I need to store the values of a currency exchange rates cross table (eg http://www.exchangerates.org.uk/currency/currency-exchange-rates-table.html ) using an RDBMS, MySql in my case.

The user is going to update the figures daily and the system will store the different versions.

I was wondering how you would design the tables or if you want the models.

The simplest way is, of course, by using a table with from, to and values columns

from: char(3)
to: char(3)
value: decimal(6,4)
inverse_value: decimal(6,4)

but I would love to know if there are other (better) solutions.

Thanks a lot.

EDIT

I apologise if it was not clear but I'm particularly interested in performances and scalability.

Keeping the value/inverse_value structure and given 90 currencies, the Currency Exchange Cross Table would need 4,050 records per day.

If a new version is created every day, in one year there would be 1,478,250 records and the queries could start to suffer.

I've implemented the table and it's working just fine, rendering the cross table is quite fast and I'm happy with it.

I was just wondering if there was a better way to implement this.

That looks like a good start, I would also add a date field (rather than a datetime field if you are only updating these values daily). So maybe something like this:

currency_code_from: char(3)
currency_code_to: char(3)
conversion_value: decimal(6,4)
inverse_conversion_value: decimal(6,4)
effective_date: date()

I am not sure what the various ways you are planning to query the table are, as this will dictate your index requirements, but I would probably use a compound primary key across the currency_code_from , currency_code_to , and effective_date fields, then add any indexes as necessary for your specific queries.

You then may want to have an additional table to relate to that stores the name of the currency and the currency symbol if needed for display (also perhaps link to country flag image if you want to use that)

currency_code: char(3)
currency_name: varchar(50)
currency_symbol: char(3)
currency_image: varchar(100)

Primary key on this table would be currency_code.

Marco, You would probably need a date field as well or a boolean isCurrent so you can select the latest ccy conversion.

Are you wanting to have buy and sell figures? Normally you make sure there is a bit of lead way between the buying and selling of ccy to make sure the organisation doesn't lose. This is called a sensible business approach by some and gouging by others.

If these figures are manually entered, make sure you look at the previous figure for the currency and if there is a discrepancy of > 3% then warn the user.

The only other issue is when exchange rates fluctuate widely over the day. Do you want to be stuck with just one conversion pre the declaration of war?

Appears that you are on the right track.

I would not personally use "natural" keys. Instead, have a table of countries/currency-having-entities:

country
-------
country_id : integer not null auto_increment
name : varchar(255)
abbrev : varchar(255)
motto : varchar(255)
. . .

then use the IDs for those in your crosstab:

currency_exchange
-----------------
currency_exchange_id : integer not null auto_increment
from_country_id : integer
to_country_id : integer 
value : decimal(10,4)
inverse_value : decimal(10,4)

This lets me change the name of the country to a symbol, full name, whatever, without having to change the crosstab table's definition. Join the two tables when querying for conversion values.

Also, I went with decimal(10,4) and I'd recommend looking up the max possible. It's not worth the programming update headache to restrict the size and to later discover that you chose a size that's too small. It doesn't take up enough space to make it worthwhile to deal with those bugs. Same for the varchar you use for the name. Varchars are stored efficiently.

Also, isn't the value always going to be 1.00? (That is, don't you always convert from 1 to some inverse in another currency?) If so, you could drop the value column from the table.

I personally like having generated ID values on all tables, so I put one on the crosstab, but some people might suggest it's unnecessary. I often find later, when I've chosen to leave it out, that I wish I had added it.

I could see having another table for the name of the currency:

currency
--------
currency_id : integer not null auto_increment
country_id : integer
name : varchar(255)
symbol : varchar(255)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM