Reputation: 431
i'd like to store multiple values of blocks into an integer in the same way as i can convert an ip into an int. My problem is that i need to do this for n blocks, not only 4. Also i need to specifiy the maximum value of each block, which is allways the same for all blocks.
So, for the Example below, if i'd like to store the whole IP range my BlockCount is 4 and my BlockSize is 255, which is the max value of each block. But it seems not to work if i lower my BlockSize and/or BlockCount.
This is my first try, but it's not working correctly:
const int BlockSize = 100;
const int BlockCount = 3;
int shiftedValues = Shift(BlockSize, BlockCount);
for (int shiftedValue = 1; shiftedValue <= shiftedValues; shiftedValue++)
{
for (int index = 0; index <= BlockCount; index++)
{
int blockValue = Unshift(index, shiftedValue);
}
}
private static int Shift(int blockSize, int blockCount)
{
int result = 0;
for (int i = 0; i < blockCount; i++)
{
result += ( blockSize << 8 * i );
}
return result;
}
private static int Unshift(int blockIndex, int shiftedValue)
{
return ( shiftedValue >> ( blockIndex * 8 ) ) & 0xFF;
}
Upvotes: 0
Views: 492
Reputation: 1362
The code above is my solution, it's pretty simple code, but feel free to ask clarification about it.
class Program
{
static void Main(string[] args)
{
int [] items = { 150 , 78 , 44 } ;
int x = Program.Pack ( items , 150 ) ;
int [] unpacked = Program.UnPack ( x , 150 , 3 ) ;
}
public static int Pack ( int[] blocks , int blockSize )
{
int size = (int)Math.Ceiling(Math.Log(blockSize, 2));
int len = size * blocks.Length;
if (len > 32)
throw new Exception("Int Limit Exceeded");
if ( blocks.Any ( x => x > blockSize ) )
throw new Exception ( "There are some blocks that exceede the maximum block size" );
List<bool> bools = new List<bool>();
bools = bools.InitBoolArray(32);
int i = 0 ;
foreach (int block in blocks)
{
BitArray temp = block.ToBinary().Take(size);
for ( int j = 0 ; j < size ; i++ , j++ )
bools[i] = temp.Get(j);
}
return (new BitArray ( bools.ToArray() ) ).ToNumeral() ;
}
public static int[] UnPack ( int entry , int blockSize , int blockCount )
{
BitArray number = entry.ToBinary();
int size = (int)Math.Ceiling(Math.Log(blockSize, 2));
if (size > 32)
throw new Exception("Int Limit Exceeded");
List<int> result = new List<int>();
for (int i = 0; i < blockCount; i++)
{
BitArray temp = number.Take(size);
number = number.Shift (size );
result.Add(temp.FitSize(32).ToNumeral());
}
return result.ToArray() ;
}
}
There extension method used
public static class BinaryConverter
{
public static BitArray ToBinary(this int numeral)
{
return new BitArray(new[] { numeral });
}
public static int ToNumeral(this BitArray binary)
{
if (binary == null)
throw new ArgumentNullException("binary");
if (binary.Length > 32)
throw new ArgumentException("must be at most 32 bits long");
var result = new int[1];
binary.CopyTo(result, 0);
return result[0];
}
public static BitArray Take (this BitArray current, int length )
{
if (current.Length < length)
throw new Exception("Invalid length parameter");
List<bool> taken = new List<bool>();
for (int i = 0; i < length; i++)
taken.Add(current.Get(i));
return new BitArray(taken.ToArray());
}
public static BitArray Shift (this BitArray current, int length )
{
if (current.Length < length)
throw new Exception("Invalid length parameter");
List<bool> shifted = new List<bool>();
for (int i = 0; i < current.Length - length; i++)
shifted.Add(current.Get(length + i));
return new BitArray(shifted.ToArray());
}
public static BitArray FitSize (this BitArray current, int size)
{
List<bool> bools = new List<bool>() ;
bools = bools.InitBoolArray(size);
for (int i = 0; i < current.Count; i++)
bools[i] = current.Get(i) ;
return new BitArray(bools.ToArray());
}
public static List<bool> InitBoolArray(this List<bool> current, int size)
{
List<bool> bools = new List<bool> ();
for (int i = 0; i < size; i++)
bools.Add(false);
return bools ;
}
}
Upvotes: 1