What should be the most recommended datatype for storing an IPv4 address in SQL server?
Or maybe someone has already created a user SQL data-type (.Net assembly) for it?
I don't need sorting.
What should be the most recommended datatype for storing an IPv4 address in SQL server?
Or maybe someone has already created a user SQL data-type (.Net assembly) for it?
I don't need sorting.
Storing an IPv4 address as a binary(4) is truest to what it represents, and allows for easy subnet mask-style querying. However, it requires conversion in and out if you are actually after a text representation. In that case, you may prefer a string format.
A little-used SQL Server function that might help if you are storing as a string is PARSENAME, by the way. Not designed for IP addresses but perfectly suited to them. The call below will return '14':
SELECT PARSENAME('123.234.23.14', 1)
(numbering is right to left).
I normally just use varchar(15) for IPv4 addresses - but sorting them is a pain unless you pad zeros.
I've also stored them as an INT in the past. System.Net.IPAddress has a GetAddressBytes method that will return the IP address as an array of the 4 bytes that represent the IP address. You can use the following C# code to convert an IPAddress to an int...
var ipAsInt = BitConverter.ToInt32(ip.GetAddressBytes(), 0);
I had used that because I had to do a lot of searching for dupe addresses, and wanted the indexes to be as small & quick as possible. Then to pull the address back out of the int and into an IPAddress object in .net, use the GetBytes method on BitConverter to get the int as a byte array. Pass that byte array to the constructor for IPAddress that takes a byte array, and you end back up with the IPAddress that you started with.
var myIp = new IPAddress(BitConverter.GetBytes(ipAsInt));
For space efficient storage and when the values are to be processed (matched or compared to a range), I use an int. The IP address really is just a 32 bit value.
For a simple solution where you just want to store the value to view it, I use a varchar(15) to store the string representation of the IP adress.
Don't forget about IPv6 - you need a lot more room if you need to store them - 128bits compares to IPv4's 32.
I'd go for bigint, though you will need some helper code to translate to human friendly versions.
One of my favorite articles talks about why you shouldn't use regular expressions to parse IP addresses. Most of what they're talking about is really explaining why you should be very careful with textual representations of IP addresses. I suggest you read it before deciding what datatype to use in your database, and probably also for whatever handling your app will be doing (even though the article is written about Perl, it's useful for any language).
I think in the end a 32 bit datatype (or four 8-bit datatypes) would be the best choice.
IPV4? int? or tinyint x 4?
It really depends on whether it's just storage and retrieval or if it's going to be a ranged search criteria.
Since an IP address has 32 bits in it, can you just use a LONG to store the numerical value?
It wouldn't be as space-wasteful as using VARCHAR, but then you'd have to decode it back to an IP before you use it, every time, and the delay and overhead that costs might not be worth it.
I've had some success with making four smallint (or whatever smallish integer datatype you prefer) columns -- one for each octet. Then, you can make a view which smashes them together as a char string (for display) or then you can write simple operators to determine who all is in what subnet etc.
It is quite fast (provided you do proper indexing) and also allows for really easy querying (no string manipulation!).
Quoting this:
Store IP addresses in a CHAR(15) column. Depending on how much data you're storing, this can be quite wasteful (why do we need to store the dots?). I