I want to generate binary data the similar to OData binary and I not sure how.
the type is defined as
Represent fixed- or variable- length binary data
binary'[A-Fa-f0-9][A-Fa-f0-9]*' OR X '[A-Fa-f0-9][A-Fa-f0-9]*' NOTE: X and binary are case sensitive. Spaces are not allowed between binary and the quoted portion. Spaces are not allowed between X and the quoted portion. Odd pairs of hex digits are not allowed.
**Example 1: X'23AB' Example 2: binary'23ABFF'**
with the next.random() Im not sure which type can be appropriate .
any idea?
new Random().nextBytes(byte[])
EDIT: You can also achieve this with
new Random().nextInt(16)
See:
int nbDigitsYouWant=8;
Random r=new Random();
for(int i=0;i<nbDigitsYouWant;i++){
//display hexa representation
System.out.print(String.format("%x",r.nextInt(16)));
}
Output:
ea0d3b9d
EDIT : Here is a quick and dirty example with random bytes sent to a DataOutputStream.
public static void main(String[] args) throws Exception{
DataOutputStream dos=new DataOutputStream(new FileOutputStream("/path/to/your/file"));
int nbDesiredBytes=99999999;
int bufferSize=1024;
byte[] buffer = new byte[bufferSize];
Random r=new Random();
int nbBytes=0;
while(nbBytes<nbDesiredBytes){
int nbBytesToWrite=Math.min(nbDesiredBytes-nbBytes,bufferSize);
byte[] bytes=new byte[nbBytesToWrite];
r.nextBytes(bytes);
dos.write(bytes);
nbBytes+=nbBytesToWrite;
}
dos.close();
}
Related
I am working on a Huffman java application and i'm almost done. I have one problem though. I need to save a String of something like: "101011101010" to a file. When I save it with my current code it saves it as characters which take up 1 byte every 0 or 1. I'm pretty sure it's possible to save every 0/1 as a bit.
I already tried some things with BitSet and Integer.valueOf but I can't get them to work. This is my current code:
FileOutputStream fos = new FileOutputStream("encoded.bin");
fos.write(encoded.getBytes());
fos.close();
Where 'encoded' is a String which can be like: "0101011101".
If I try to save it as integer the leading 0 will be removed.
Thanks in advance!
EDIT: Huffman is a compression method so the outputted file should be as small as possible.
I think I found my answer. I put the 1's and 0's in a BitSet using the following code:
BitSet bitSet = new BitSet(encoded.length());
int bitcounter = 0;
for(Character c : encoded.toCharArray()) {
if(c.equals('1')) {
bitSet.set(bitcounter);
}
bitcounter++;
}
After that I save it to the file using bitSet.toByteArray()
When I want to read it again I convert it back to a bitset using BitSet.valueOf(bitSet.toByteArray()). Then I loop through the bitset like this:
String binaryString = "";
for(int i = 0; i <= set.length(); i++) {
if(set.get(i)) {
binaryString += "1";
} else {
binaryString += "0";
}
}
Thanks to everyone who helped me.
Binary files are limited to storing bits in multiples of eight. You can solve this problem by chopping the string into eight-bit chunks, converting them to bytes using Byte.parseByte(eightCharString, 2) and adding them to a byte array:
Compute the length of the byte array by dividing the length of your bit string by eight
Allocate an array of bytes of the desired length
Run a loop that takes substrings from the string at positions representing multiples of eight
Parse each chunk, and put the result into the corresponding byte
Call fos.write() on the byte array
Try this.
String encoded = "0101011101";
FileOutputStream fos = new FileOutputStream("encoded.bin");
String s = encoded + "00000000".substring(encoded.length() % 8);
for (int i = 0, len = s.length(); i < len; i += 8)
fos.write((byte)Integer.parseInt(s.substring(i, i + 8), 2));
fos.close();
I'm having trouble finding what I'm looking for. Is there anyway to read a file by hexadecimal values in java, and to write another file? If I wanted to take one file and create a new file where every hexadecimal value was incremented, how would I do this? Like if I had a txt file that said "Hello" and I increment every hexadecimal value so that it should say "Ifmmp".
How do I read a file (any file, not just an ASCII text file) hexadecimal by hexadecimal, and write another file one hexadecimal at a time?
I believe this is what you're looking for...
Here's code to read from a file and take the hex values of each part in file.
/*
Code which defines a scanner class and FileInputStream
*/
String lineInFile = scannerName.nextLine();
int[] convertMeToHex = new int[lineInFile.length()];
for (int i = 0; i < convertMeToHex.length; i++)
convertMeToHex[i] = (int) lineInFile.charAt(i);
String[] hex = new String[convertMeToHex.length];
for (int i = 0; i < convertMeToHex.length; i++)
hex[i] = Integer.toHexString(convertMeToHex[i]));
You can convert hex back to int with int hexToInt = Integer.parseInt(hexNumber, 16);
I'm trying to answer the question below:
Use an array or ArrayList and generate 20 random numbers (Integer
values between 0 and 100. 100 not inclusive). The program should
perform the following tasks.
Write the numbers from the array or ArrayList to a file.
Read the numbers from the file and display them on the console in decimal, hexadecimal and binary.
So far I have the random generator working well, and the file is being written. As for re-reading the file and displaying the numbers from the file as hex, decimal and binary...I am completely lost. Here is that I have so far.
import java.io.DataOutputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Random;
public class Write {
public static void main(String[] args) throws IOException {
Random generator = new Random();
ArrayList numList = new ArrayList();
int n = 0;
while( n < 20 ) {
int numGen = generator.nextInt(100);
numList.add(numGen);
n++;
}
String result = numList.toString().replaceAll("[\\[\\]]", "");
result = result.replace(",", " ");
System.out.print(result);
String filePath = "C:/Users/Username/Desktop/FileIOTest/coding_assignment.txt";
File f = new File(filePath);
FileOutputStream fileout = new FileOutputStream (f);
DataOutputStream dataOut = new DataOutputStream(fileout);
dataOut.writeBytes(result);
dataOut.close();
}
}
I guess you should try to complete the lines by yourself, so I only give you some basic input.
To read from file, three lines:
fileIn
dataIn
readBytes
These lines should be easy. To get the numbers, use
split
Integer.ParseInt
and to display, you may refer to
Integer.toHexString
Integer.toBinaryString
From your code, you have not started to write the code for Reading numbers from file.
Regarding reading the values, you can use BurreferReader to read numbers line by line. And then you can use String.split method to split the numbers into an array using split(" ")
Regarding converting int value to Binary and Hex mode, you can use the method toBinaryString and toHexString in Integer class, like
int i = 20;
System.out.println(i);//Print int value
System.out.println(Integer.toBinaryString(i)); //Print Binary string
System.out.println(Integer.toHexString(i)); // Print Hex string
Output in Console is as follows:
20
10100
14
To convert numbers to binary and hexadecimal from base 10, you can simply use the methods:
Integer.toBinaryString(n);
Integer.toHexString(n);
However, if you actually want to code these for yourself, try checking out the following website:
http://www.cs.umd.edu/class/sum2003/cmsc311/Notes/Data/toBaseK.html
It helps provide a simple algorithm that converts from base 10 to any other number base.
I have a problem with parsers.
The problem is I get an integer such as "8" and I need to transform this to an 8-bit unsigned byte.
Later on I will receive an integer "56" and need to transform it using the the same method but when I get a "-53" (for example) I shall say that was a mistake in the communication and sending.
For example,
number = 538; //or 63492873 or 8 or 17826312631 or -231 or whatever
try{
byte response[] = Parse8BitUnsigned(number);
}catch(Idkexcepcion ex){
System.out.println("the number is a signed one");
byte response[] = Parse8BitSigned(number);
}
Note: Parse8BitSigned() and Parse8BitSigned() had not been implemented. I need that method for any number
You can use ByteBuffer to do what you want:
String number="8";
int num = Integer.valueOf(number);
if(num < 0 ) //ERROR
// Return 8 in a 4 bytes array
byte[] bytes = ByteBuffer.allocate(4).putInt(num).array();
I need to compute a numeric representation of a string which is bi-direction. For example, If I have a string "US" I would like an algorithm which when applied to "US" generates a number X (int or long). When another algorithm is applied to X, I want to get "US". Each string consists of two characters.
Thanks in advance.
The following does it easily by using DataInputStream and DataOutputStream to read/write to an underlying byte array.
public static void main(String[] args) {
String original = "US";
int i = stringToInt(original);
String copy = intToString(i);
System.out.println("original: "+original);
System.out.println("i: "+i);
System.out.println("copy: "+copy);
}
static int stringToInt(String s) {
byte[] bytes = s.getBytes();
if (bytes.length > 4) {
throw new IllegalArgumentException("String too large to be" +
" stored in an int");
}
byte[] fourBytes = new byte[4];
System.arraycopy(bytes, 0, fourBytes, 0, bytes.length);
try {
return new DataInputStream(new ByteArrayInputStream(fourBytes))
.readInt();
} catch (IOException e) {
throw new RuntimeException("impossible");
}
}
static String intToString(int i) {
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
try {
new DataOutputStream(byteArrayOutputStream).writeInt(i);
} catch (IOException e) {
throw new RuntimeException("impossible");
}
return new String(byteArrayOutputStream.toByteArray());
}
This is in the general sense impossible; there are only 2^64 long values, and there are more than 2^64 64-character strings consisting only of the characters X, Y and Q.
Maybe you want to have a pair of hash tables A and B and a counter; if you're given a string you check whether it's in the first hash table, if so return the value you stored there, if not then you set
A[string]=counter; B[counter]=string; counter=1+counter;
What you're describing is bidirectional encryption. Something like this may help you. Another way to do this if you specifically want a numerical value, is to store the character codes (ASCII codes) of each letter. However the resulting number is going to be huge (especially for really long strings) and you probably won't be able to store it in an 32 or 64-bit integer. Even a long won't help you here.
UPDATE
According to your edit, which says that you only need two characters, you can use the ASCII codes by using getBytes() on the String. When you need to convert it back, the first two digits will correspond to the first character, whereas the last two will correspond to the second character.
This could do, assuming your Strings have length 2, i.e. consist of two Java char values:
public int toNumber(String s) {
return s.charAt(0) + s.charAt(1) << 16;
}
public String toString(int number) {
return (char)number + "" + (char)(number >> 16);
}
There are Unicode characters (those with numbers over 216) that do not fit into a single Java char, but are represented (by UTF-16) by two consecutive surrogates. This algorithm would work for a single-Character-string consisting of these two surrogates, but not for longer strings consisting of more than one such character.
Also, there are int values which do not map back to valid Unicode (or UTF-16) strings (e.g. which produce unpaired surrogates instead of valid characters). But each normal string gets converted to an int and back to the same string.