13

Example:

// using Integer.parseInt
int i = Integer.parseInt("123");

How would you do the same for?

// using Integer.parseInt
int i = Integer.parseInt("123.45.55.34");
Brane
  • 139
  • 1
  • 2
  • 6
  • May i know why you required that? – Subhrajyoti Majumder Aug 21 '12 at 15:09
  • Perhaps `InetAddress.getByName("123.45.55.34")` is more useful than the address as an `int` value. – Peter Lawrey Aug 21 '12 at 15:15
  • @PeterLawrey thanks for your reply, I am having problem with parsing the dotted IP numbers in my queries. I have updated my question :) – Brane Aug 21 '12 at 15:30
  • 1
    You can use the hashCode() returned by this expression but its a bit of a hack. – Peter Lawrey Aug 21 '12 at 15:35
  • 1
    Your latest edit made most of the answers useless. Please consider asking new questions when making major semantic changes through edits – Lukas Eder Aug 21 '12 at 15:45
  • Mr lUkas, thanks for your remark however all the answers have been helpful :) – Brane Aug 21 '12 at 15:53
  • @Brane, the problem is now when someone else finds this question none of the answers will make sense in the context of how the question is currently worded. If you had instead created a new question all of the existing answers would continue to be valuable to future users who are having the problem you originally described. – Mike Deck Aug 21 '12 at 16:27
  • thanks @ Mike Deck, i was asked to provide more detailed if you do read at the top of this thread `May i know why you required that? – Quoi 1 hour ago` In all fairness if you think it's anyhow a mess please just delete your own code. thanks :) – Brane Aug 21 '12 at 16:38
  • I agree with Mike, now the question seems unclear – Hi computer Jan 16 '23 at 11:13

8 Answers8

20

You're likely to want to do this:

// Parse IP parts into an int array
int[] ip = new int[4];
String[] parts = "123.45.55.34".split("\\.");

for (int i = 0; i < 4; i++) {
    ip[i] = Integer.parseInt(parts[i]);
}

Or this:

// Add the above IP parts into an int number representing your IP 
// in a 32-bit binary form
long ipNumbers = 0;
for (int i = 0; i < 4; i++) {
    ipNumbers += ip[i] << (24 - (8 * i));
}

Of course, as others have suggested, using InetAddress might be more appropriate than doing things yourself...

Community
  • 1
  • 1
Lukas Eder
  • 211,314
  • 129
  • 689
  • 1,509
19

You can do it for an IP V4 adress as the parts are just the four bytes of the integer version.

Do this to convert an InetAdress to its integer representation :

int result = 0;  
for (byte b: inetAdress.getAddress())  
{  
    result = result << 8 | (b & 0xFF);  
}

Note that you shouldn't use 32 bits integers for IP addresses now, as we're entering the era of IPV6 addresses.

EDIT : to parse a string like "123.45.55.34" to something useful in java, you may use INetAddress.getByName(yourString)

Denys Séguret
  • 372,613
  • 87
  • 782
  • 758
  • salut @ dystroy, Comment this code that you have provided pourra s'appliquer to my question, I have plus de precision to the question. merci monsieur :) – Brane Aug 21 '12 at 15:57
  • This is a really different question now. I edited my answer but this starts to be a mess... – Denys Séguret Aug 21 '12 at 16:12
  • 3
    Using getByName is probably a bad idea if all you're meaning to do is parse an IP address, since if you're given a hostname instead you'll suddenly be doing synchronous network I/O. – Glenn Maynard Mar 25 '15 at 16:58
7

You need to realize that an IPv4 address in the form 123.45.55.34 is actually 4 three digit numbers representing each byte of the address. Parsing the entire string all at once won't work.

Others have mentioned using an InetAddress, but if all you have is a string representation of the IP you can't easily instantiate an InetAddress as far as I know.

What you can do is something like the following:

public static int parseIp(String address) {
    int result = 0;

    // iterate over each octet
    for(String part : address.split(Pattern.quote("."))) {
        // shift the previously parsed bits over by 1 byte
        result = result << 8;
        // set the low order bits to the current octet
        result |= Integer.parseInt(part);
    }
    return result;
}
Mike Deck
  • 18,045
  • 16
  • 68
  • 92
7

The IPAddress Java library supports both IPv4 and IPv6 in a polymorphic manner. Disclaimer: I am the project manager of that library.

The following code works with both IPv4 and IPv6 addresses. Using your example IPv4 address:

IPAddress addr = new IPAddressString("123.45.55.34").getAddress();
BigInteger value = addr.getValue(); // 2066560802

If IPv4, you can just go straight to an int value:

if(addr.isIPv4()) {
    int val = addr.toIPv4().intValue(); // 2066560802
}
Sean F
  • 4,344
  • 16
  • 30
3
System.out.println(
        ByteBuffer.allocate(Integer.BYTES)
        .put(InetAddress.getByName("0.0.1.0").getAddress())
        .getInt(0));

Output:

256

atoMerz
  • 7,534
  • 16
  • 61
  • 101
1

I think you might be misunderstanding your own problem. Are you trying to convert that into a single int value? If you are doing that then the premise of your question is wrong because IP numbers are not one number but multiple byte values. It isn't 123,456,789,000 but rather byte 123 byte 455 byte 789 and byte 000. I know that these are not real byte numbers but the point is is that this is not 123 billion 456 million 789 thousand,000. It seems to me that you are treating the entire thing as a single integer and that isn't the case with IP addresses.

Tim
  • 11
  • 1
0

Sorry for reopening an old queston, but to me seems like it's missing a possible valid and performant solution:

static int ipV4ToInt(int a1, int a2, int a3, int a4){
  return (a1 << 24) ^ (a2 << 16) ^ (a3 << 8) ^ a4;
}

then you can add parsing and validation:

class MyAwesomeIPv4Utils {
  private MyAwesomeIPv4Utils(){} // It's a library, sorry OOP addicted...

  static int validateIpPart(int n){
    if (n < 0 || n > 255)
      throw new IllegalArgumentException("Invalid IP v4 part: " + n);
    return n;
  }
  
  static int validateIpPart(String p){
    return validateIpPart(Integer.parseInt(p));
  }
  
  static int internalIpV4ToInt(int a1, int a2, int a3, int a4){
    // let validation outside, just for performance reasons (e.g. inlining and lazy evaluation): it can be made by the caller
    return (a1 << 24) ^ (a2 << 16) ^ (a3 << 8) ^ a4;
  }
  
  // this can be made public as it handles the validation, and can be used to directly create int when you know the addresses at comple time
  public static int ipV4ToInt(int a1, int a2, int a3, int a4){
    return internalIpV4ToInt(
      validateIpPart(a1),
      validateIpPart(a2),
      validateIpPart(a3),
      validateIpPart(a4)
    );
  }
  
  // this can be exposed too, as it handles both validation and parsing
  public static int ipV4ToInt(String ipStr){
    Objects.requireNonNull(ipStr, "null IP Address");
    // If you prefer you can make this Pattern a static variable, to create it just once and shared (Patterns are thread-safe), but be careful with it's instantiation as it can be null at the first invokation of this static method
    final Pattern ipPattern = Pattern.compile("(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})");
    final Matcher m = ipPattern.matcher(ipStr);
    if (!m.matches())
      throw new IllegalArgumentException("Invalid IP v4 address: " + ipStr);

    return internalIpV4ToInt(
      validateIpPart(m.group(1)),
      validateIpPart(m.group(2)),
      validateIpPart(m.group(3)),
      validateIpPart(m.group(4))
    );
  }
}
-1

IPAddressUtil#textToNumericFormatV4 performs better than String#split to get bytes of ip, besides, it checks if the ip is valid

 public int intOfIpV4(String ip) {
        int result = 0;
        byte[] bytes = IPAddressUtil.textToNumericFormatV4(ip);
        if (bytes == null) {
            return result;
        }
        for (byte b : bytes) {
            result = result << 8 | (b & 0xFF);
        }
        return result;
    }
Arthur Xu
  • 441
  • 1
  • 5
  • 12