$size, $bits, verilog - arrays

What is the difference between $size and $bits operator in verilog.?
if I've variables, [9:0]a,[6:0]b,[31:0]c.
c <= [($size(a)+$size(b)-1]-:$bits(b)];
What will be the output at 'c' from the above expression?

$size() gives the number of bits for a single dimension. $bits() gives the number of bits to completely represent the variable.
For example:
reg [9:0] a;
reg [9:0] b [5:0];
initial begin
$display("a Size ", $size(a));
$display("a Bits ", $bits(a));
$display("b Size ", $size(b));
$display("b Bits ", $bits(b)) ;
end
Gives :
a Size 10
a Bits 10
b Size 6 // Depth of memory
b Bits 60 // Width * Depth
In your case you just have 1 dimensional arrays, not memories or structs so $size() and $bits() would be the same thing.

$size shall return the number of elements in the dimension, which is equivalent to $high - $low + 1. It is relative to the dimension, not only bit counts. If the type is 1D packed array or integral type, it is equal to $bits.
$bits system function returns the number of bits required to hold an expression as a bit stream.
$bits ( [expression|type_identifier] )
It returns 0 when called with a dynamically sized type that is currently empty. It is an error to use the $bits system function directly with a dynamically sized type identifier.
I have no idea about your question, c <= [($size(a)+$size(b)-1]-:$bits(b)];. Is it a valid expression in RHS? Are you talking about the array range expression, [n +: m] or [n -: m] ?

Related

Find Minimum Operand to Maximize sum of bitwise AND operator

Given an array of integers Arr and an integer K, bitwise AND is to be performed on each element A[i] with an integer X
Let Final sum be defined as follows:
Sum of ( A[i] AND X ) for all values of i ( 0 to length of array-1 )
Return the integer X subject to following constraints:
Final sum should be maximum
X should contain exactly K bits as 1 in its binary representation
If multiple values of X satisfy the above conditions, return the minimum possible X
Input:
Arr : [8,4,2]
K = 2
Output: X=12
12 Contains exactly 2 bits in its binary and is the smallest number that gives maximum possible answer for summation of all (A[i] AND X)
Approach Tried :
Took bitwise OR for all numbers in the array in binary and retained the first K bits of the binary that had 1 , made remaining bits 0, convert back to int
Passed 7/12 Test Cases
Can someone help me out with what mistake am I making with regards to the approach or suggest a better approach ? Thanks in advance.
Consider an input like [ 8, 4, 4, 4 ], K = 1. Your algorithm will give 8 but the correct answer is 4. Just because a given bit is more significant doesn't mean that it will automatically contribute more to the sum, as there might be more than twice as many elements of the array that use a smaller bit.
My suggestion would be to compute a weight for each bit of your potential X -- the number of elements of the array that have that bit set times the value of that bit (2i for bit i). Then find the K bits with the largest weight.
To do this, you need to know how big your integers are -- if they are 32 bits, you need to compute just 32 weights. If they might be bigger you need more. Depending on your programming language you may also need to worry about overflow with your weight calculations (or with the sum calculation -- is this a true sum, or a sum mod 2n for some n?). If some elements of the array might be negative, how are negatives represented (2s complement?) and how does that interact with AND?
Let dp[k][i] represent the maximum sum(a & X), a ∈ array, where i is the highest bit index in X and k is the number of bits in X. Then:
dp[1][i]:
sum(a & 2^i)
dp[k][i]:
sum(a & 2^i) + max(dp[k-1][j])
for j < i
sum(a & 2^i) can be precalculated for all values of i in O(n * m), where m is the word size. max(dp[k-1][j]) is monotonically increasing over j and we want to store the earliest instance of each max to minimise the resulting X.
For each k, therefore, we iterate over m is. Overall time complexity O(k * m + n * m), where m is the word size.

Storage order for multidimensional arrays in C

With a C compiler, are array elements are stored in column major order or row major order, or it is compiler dependent?
int arr[2][3]={1,2,3,4,5,6};
int array[3][2]={1,2,3,4,5,6};
on printing arr and array output:
arr:
1 2 3
4 5 6
array:
1 2
3 4
5 6
It seems its always prefer row major order?
Row major order is mandated by the standard.
6.5.2.1p3:
Successive subscript operators designate an element of a
multidimensional array object. If E is an n-dimensional array (n >= 2)
with dimensions i x j x . . . x k, then E (used as other than an
lvalue) is converted to a pointer to an (n - 1)-dimensional array with
dimensions j x . . . x k. If the unary * operator is applied to this
pointer explicitly, or implicitly as a result of subscripting, the
result is the referenced (n - 1)-dimensional array, which itself is
converted into a pointer if used as other than an lvalue. It follows
from this that arrays are stored in row-major order (last subscript
varies fastest).
(Emphasis mine)
You printed the array. The output is in whatever order that you printed the array elements. So what you see has nothing to do with the order in which array elements are stored in memory.
int arr[2][3] means that you have three arrays, and the object stored in each array is an int[2]. Objects are always stored consecutively, so the first int[2] is stored in consecutive memory, followed by the second int[2], followed by the third int[2]. And that is the same for any C implementation.

how to find cell index no. in 2-D array?

in C programming if an 2-D array is given like ( int a[5][3]) and base address and address of particular element (cell ) is also given and have to find index no. of that element(cell) (row and col no.) can we find that? if yes how?
i know the formula of finding address is like this
int a[R][C];
address(a[i][j])=ba+size(C*i+ j);
if ba, R,C,Size and address(a[i][j]) is given... how to find value of i and j?
for finding the value of 2 variable we need 2 equation ..but im not able to find 2nd equation.
The specific address minus the base address gives you the size in bytes, from the base to the specific address.
If you divide that size in bytes with sizeof(ba[0][0]) (or sizeof(int)), you get the number of items.
items / C gives you the first dimension and items % C gives you the second dimension.
Thus:
int ba[R][C];
uintptr_t address = (uintptr_t)&ba[3][2]; // some random item
size_t items = (address - (uintptr_t)ba) / sizeof(ba[0][0]);
size_t i = items / C;
size_t j = items % C;
It is important to carry out the arithmetic with some type that has well-defined behavior, therefore uintptr_t.
If I had done int* address then address - ba would be nonsense, since ba decays into an array pointer of type int(*)[3]. They aren't compatible types.
Use integer division and remainder operators.
If you have the base and a pointer to an element, elt, then there are two things:
In "pure math" terms, you'll have to divide by the size of the elements in the array.
In "C" terms, when you subtract pointers this division is performed for you.
For example:
int a[2];
ptrdiff_t a0 = (ptrdiff_t)&a[0];
ptrdiff_t a1 = (ptrdiff_t)&a[1];
a1 - a0; // likely 4 or 8.
This will likely be 4 or 8 because that's the likely size of int on whatever machine you're using, and because we performed a "pure math" subtraction of two numbers.
But if you let C get involved, it tries to do the math for you:
int a[2];
int * a0 = &a[0];
int * a1 = &a[1];
a1 - a0; // 1
Because C knows the type, and because it's the law, the subtracted numbers get divided by the size of the type automatically, converting the pointer difference into an array-like index or offset.
This is important because it will affect how you do the math.
Now, if you know that the address of elt is base + SIZE * (R * i + j) you can find the answer with integer division (which may be performed automatically for you), subtraction, more integer division, and either modulus or multiply&subtract:
offset or number = elt - base. This will either give you an index (C style) or a numeric (pure math) difference, depending on how you do the computation.
offset = number / SIZE. This will finish the job, if you need it.
i = offset / R. Integer division here - just throw away the remainder.
j = offset - (i*R) OR j = offset % R. Pick what operation you want to use: multiply & subtract, or modulus.

what does this code line do?

Hi I am new to C programming can anyone please tell me what this line of code would do:
i = (sizeof (X) / sizeof (int))
The code actually works with a case statement when it takes a value of bdata and compares it to different cases.
Generally, such a statement is used to calculate the number of elements in an array.
Let's consider an integer array as below:
int a[4];
Now, when sizeof(a) is done it will return 4*4 = 16 as the size. 4 elements and each element is of 4 bytes.
So, when you do sizeof(a) / sizeof(int), you will get 4 which is the length or size of the array.
It computes the number of elements of the array of int named X.
returns the length of the array X
it computes X's volume in memory divided by the size of an integer in your computer(2 bytes or 4 bytes). If i is integer than it is an integer division. If it is float and X has no even volume, it is real division.
int size can change. X depends on implementation. Division result depends on type of i.
All these means, it computes how many ints fit into X.
Besides common practice or personal experience there is no reason to think that this i = (sizeof (X) / sizeof (int)) computes the size of the array X. Most often probably this is the case but in theory X could be of any type, so the given expression would compute the ratio of the sizes of your var X and an int (how much more memory, in bytes, does your X var occupy with respect to an int)
Moreover, if X was a pointer to an array (float* X, the alternate way of declaring arrays in C) this expression would evaluate to 1 on a 32-bit architecture. The pointer would be 4 bytes and the int also 4 bytes => i = sizeof(X) / sizeof(int) (=1)

2-D array in C, address generation

How do addresses get generated in arrays in C, say how does a [x][y] get to a particular value, i know its not that big a question but just about to actually start coding.
Well it is done depending on your data type of whose array you have considered.
Say for an Integer array, each value holds 4 bytes, thus a row X long will take 4X bytes.
Thus a 2-D matrix of X*Y will be of 4*X*Y Bytes.
Any address say Arry[X][Y] would be
calculated as : (Base Address of Arry)
+ (X * No. of columns) + ( Y // Offset in current row )
2-dimensional arrays in C are rectangular. For example:
int matrix[2][3];
allocates a single block of memory 2*3*sizeof(int) bytes in size. Addressing matrix[0][1] is just a matter of adding 0 * (3 * sizeof(int)) to sizeof(int). Then add that sum to the address at which matrix starts.
A nested array is an array of arrays.
For example, an int[][6] is an array of int[6].
Assuming a 4-byte int, each element in the outer array is 6 * 4 = 24 bytes wide.
Therefore, arr[4] gets the third array in the outer array, or *(arr + 4 * 24).
arr[4] is a normal int[]. arr[4][2] gets the second int in this inner array, or *(arr + 4 * 24 + 2 * 4)
E.g.
char anArray[][13]={"Hello World!","February","John"};
You can visualize it as:
anArray:
H|e|l|l|o| |W|o|r|l|d|!|\0|F|e|b|r|u|a|r|y|\0|\0|\0|\0|\0|J|o|h|n|\0|\0|\0|0|\0
^ ^ ^
0 13 26

Resources