A matrix B (consisting of integers) of dimension N × N is said to be good if there exists an array A (consisting of integers) such that B[i][j] = |A[i] - A[j]|, where |x| denotes absolute value of integer x.
You are given a partially filled matrix B of dimension N × N. Q of the entries of this matrix are filled by either 0 or 1. You have to identify whether it is possible to fill the remaining entries of matrix B (the entries can be filled by any integer, not necessarily by 0 or 1) such that the resulting fully filled matrix B is good.
Example
Input 4
2 2
1 1 0
1 2 1
2 3
1 1 0
1 2 1
2 1 0
3 2
2 2 0
2 3 1
3 3
1 2 1
2 3 1
1 3 1
Output
yes
no
yes
no
Here is my code, but failing some tests.
include int main(){
int t;
scanf("%d", &t);
while(t--){
int n, q;
scanf("%d %d", &n, &q);
int arr[n][n];
int brr[n];
for(int i=0;i<n;i++){
brr[i]=1;
for(int j=0;j<n;j++)
arr[i][j]=-1;
}
int result=0;
while(q--){
int l, r, val;
scanf("%d %d %d", &l, &r, &val);
arr[l-1][r-1]=val;
arr[r-1][l-1]=val;
if( abs(brr[l-1]-brr[r-1])!=val && l!=r){
brr[r-1]=brr[r-1]-val;
}
}
for(int i=0;i<n;i++)
printf("%d ", brr[i]);
printf("\n");
for(int i=0;i<n;i++){
for(int j=0;j<n;j++){
if(arr[i][j]!=-1 ){
if( abs(brr[i]-brr[j])==arr[i][j] && abs(brr[i]-brr[j])==arr[j][i]){
continue;
}
else{
result=1;
break;
}
}
}
if(result)
break;
}
if(result)
printf("no\n");
else
printf("yes\n");
}
return 0; }
The question is from live contest : https://www.codechef.com/SEPT17/problems/FILLMTR/. Please focus on learning rather than increase the count of accepted problems.
Related
Hi I'v been trying to write Hoare's partition function for like 5 hours now. I read this and this and even straight up copied the "correct" function from these questions and it's still nowhere near the answer. Here is my "translated" code from Cormen's book.
int Hpartition(int A[], int p, int r){
int x = A[p];
int i = p - 1;
int j = r + 1;
while(true){
do{
j--;
}while(A[j] <= x);
do{
i++;
}while(A[i] >= x);
if(i < j){
swap(A[i],A[j]);
}
else
return j;
}
}
QuickSort:
void qs(int A[],int p,int r){
if(p<r){
int q=Hpartition(A,p,r);
qs(A,p,q-1);
qs(A,q+1,r);
}
}
Main:
int main(int argc, const char * argv[]) {
int tab[10];
for(int k=0;k<10;k++){
cin >> tab[k];
}
qs(tab,0,9);
for(int i=0;i<10;i++){
cout << tab[i] << " ";
}
return 0;
}
For this data :
2 4 1 3 5 7 6 8 10 9
It produces this result:
2 4 9 3 5 7 6 8 10 1
Based on the previous questions regarding the topic I know there may be some mistakes in the book. But even when I apply the answers from the previous questions it just won't work .
Here is the algorithm from the book:
HOARE-PARTITION(A, p, r)
1 x = A[p]
2 i = p - 1
3 j = r + 1
4 while TRUE
5 repeat
6 j = j - 1
7 until A[j] <= x
8 repeat
9 i = i + 1
10 until A[i] >= x
11 if i < j
12 exchange A[i] with A[j]
13 else return j
Thanks in advance for any help.
You have 2 error translating code from book:
do{
j--;
}while(A[j] <= x);
You should inverse this:
do{
j--;
}while(A[j] > x);
The same with:
do{
i++;
}while(A[i] >= x);
And one more here:
qs(A,p,q-1);
qs(A,q+1,r);
Change to:
qs(A,p,q);
qs(A,q+1,r);
This is a recent interview question from Google:
We define f(X, Y) as number of different corresponding bits in binary
representation of X and Y. For example, f(2, 7) = 2, since binary
representation of 2 and 7 are 010 and 111, respectively. The first and
the third bit differ, so f(2, 7) = 2.
You are given an array of N positive integers, A1, A2 ,…, AN. Find sum
of f(Ai, Aj) for all pairs (i, j) such that 1 ≤ i, j ≤ N
For example:
A=[1, 3, 5]
We return
f(1, 1) + f(1, 3) + f(1, 5) + f(3, 1) + f(3, 3) + f(3, 5) + f(5, 1) +
f(5, 3) + f(5, 5) =
0 + 1 + 1 + 1 + 0 + 2 + 1 + 2 + 0 = 8
I could think of this solution which is O(n^2)
int numSetBits(unsigned int A) {
int count = 0;
while(A != 0) {
A = A & (A-1);
count++;
}
return count;
}
int count_diff_bits(int a, int b)
{
int x = a ^ b;
return numSetBits(x);
}
for (i = 0; i < n; i++)
for (j = 0; j < n; j++) {
sum += count_diff_bits(A[i], A[j]);
}
}
Another approach i can think of is (considering that each element contains only one binary digit):
Start from the end of the array
keep a count of 1's and 0's found so far
If the current element is 1, then it will contribute count_of_zeros to the final sum
Continue like this till we reach the start of the array.
Is this approach correct.
Iterate the array, and count number of "on" bits in each bit index, for example [1, 3, 5]:
0 0 1
0 1 1
1 0 1
-----
1 1 3
Now, for each bit counter, calculate:
[bit count] * [array size - bit count] * 2
and sum for all bits...
With example above:
3 * (3 - 3) * 2 = 0
1 * (3 - 1) * 2 = 4
1 * (3 - 1) * 2 = 4
total = 8
To show why this works, lets look at a subset of the problem, using a single bit. Let's see what happens if we have an array with: [1, 1, 0, 0, 1, 0, 1]. Our count is 4 and size is 7. If we examine the first bit with all the bits in the array (including self, as in the question), we get:
1 xor 1 = 0
1 xor 1 = 0
1 xor 0 = 1
1 xor 0 = 1
1 xor 1 = 0
1 xor 0 = 1
1 xor 1 = 0
As can be seen, the contribution of this bit is the number of "off" bits. The same holds true for any other "on" bit. We could say that each "on" bit counts as the number of "off" bits:
[bit count] * [array size - bit count]
And where does the multiplication by 2 comes from? well, since we do the same with the "off" bits, except that for these, the contribution is the number of "on" bits:
[array size - bit count] * [bit count]
which of course is the same as above, and we can just multiply...
Complexity is O(n*k) where k is number of bits (32 in your code).
#include <bits/stdc++.h>
#define MOD 1000000007ll
using namespace std;
typedef long long LL;
int solve(int arr[], int n) {
int ans = 0;
// traverse over all bits
for(int i = 0; i < 31; i++) {
// count number of elements with ith bit = 0
long long count = 0;
for(int j = 0; j < n; j++) if ( ( arr[j] & ( 1 << i ) ) ) count++;
// add to answer count * (n - count) * 2
ans += (count * ((LL)n - count) * 2ll) % MOD;
if(ans >= MOD) ans -= MOD;
}
return ans;
}
int main() {
int arr[] = {1, 3, 5};
int n = sizeof arr / sizeof arr[0];
cout << solve(arr, n) << endl;
return 0;
}
I recently encountered this problem in an interview
There are n stairs, a person standing at the bottom wants to reach the top. The person can climb either 1 stair or 2 stairs at a time.
Print all possible ways person can reach the top.
For example, n=4 Output:
1 2 3 4
1 2 4
1 3 4
2 3 4
2 4
But I couldn't code this properly. How to code up solution for this?
To print the number of ways, you can first understand how to calculate the number of ways, and adjust it so each "count" will print instead of just count:
D(0) = 1
D(-1) = 0
D(i) = D(i-1) + D(i-2)
To adjust it to actual printing, you need to "remember" the choices you have made, and follow the same logic. Pseudo code:
printWays(curr, n, soFar):
if curr > n:
return
soFar.append(curr)
if n == curr:
print soFar
soFar.removeLast()
return
printWays(curr+1,n,soFar)
printWays(curr+2,n,soFar)
soFar.removeLast()
The idea is:
soFar is the current series of steps you did.
curr is the current step you're at.
n is the last stair you need to get to.
At each point, you either climb one stair or two. You check both options.
You can try some recursive solution where you call recursively CanClimb(n-1) and CanClimb(n-2) to visualize the possible ways.
Sample solution in C#:
public static void ClimbWays(int n, int currentIndex, int[] currectClimb)
{
if (n < 0) return;
if (n == 0)
{
for (var i = currentIndex - 1; i >= 0; i--)
{
Console.Write(currectClimb[i] + " ");
}
Console.WriteLine();
return;
}
currectClimb[currentIndex] = n;
ClimbWays(n - 1, currentIndex + 1, currectClimb);
ClimbWays(n - 2, currentIndex + 1, currectClimb);
}
Output for ClimbWays(4, 0, new int[4]);:
1 2 3 4
2 3 4
1 3 4
1 2 4
2 4
If you want to just count them you can use the well known Fibonacci sequence which can be calculated iteratively:
public static int Fibonacci(int n)
{
int a = 0;
int b = 1;
// In N steps compute Fibonacci sequence iteratively.
for (int i = 0; i < n; i++)
{
int temp = a;
a = b;
b = temp + b;
}
return a;
}
We are given square binary matrix with side n.
We will consider any row or column which contains at least one 0 as 'bad'.
Task is to nullify all bad rows and columns.
Task requires to use O(1) of additional memory.
1 1 0 0 0 0
1 1 1 => 1 0 0
1 0 1 0 0 0
Tough thing is, that we cannot nullify bad lines as we discover them during traversal (otherwise we will always end up with zeroed matrix). So I am looking for such a data structure or such a way of data representation, so it could store all info about bad rows and columns while algorithm is iterating through matrix.
Actually we only need 2n bits to get the answer: we need to know for each row and column if it is good (1) or bad (0). The answer in each cell would be product of the answers for row and column.
Let's store most of that information in the matrix itself:
we can use first row to keep records (0 or 1) for all columns but first,
first column to keep records for all rows but first, and we need two more bits to keep records for first row and first column.
At first we get those two additional bits (checking first row and first column).
Then find and store records for other rows and columns.
Then calculate resulting bits in all the matrix except for first row and column.
And finally: first row should be nullified if it was bad and kept as it is otherwise, and the same is to be done with the first column.
As the first step, look for a 0 in the grid. If we can't find one, we're done.
If we found one, we know that we're supposed to nullify all 1's in the 0's row and column.
So, since we know the final value of all those cells, we could use that row and column as temporary boolean flags for whether the same row or column contains any 0's.
The exact process:
Look through the matrix to find a 0.
Keeping track of the coordinates of the found 0.
Looping over each row and column, checking whether that row or column contains a 0, and setting the flag appropriately.
Then looping over the matrix again and, for each 1 not in the flag row or column, checking whether either the row or the column flag is set, and, if it is, set that 1 to 0.
Then setting all cells in the row and column acting as flags to 0.
This runs in linear time (O(mn) with m rows and n columns) and O(1) space.
Example:
Input:
1 1 0 1 0
1 1 1 0 1
1 0 1 1 1
1 1 1 1 1
1 1 1 1 1
Then we look for a zero, and let's say we find the top-middle one.
Then we use the top row and middle column as flag for whether the same row / column contains a 0:
0 1 0 1 1
1
1
0
0
Then we loop over the other cells setting the 1's to 0's if the flag row / column is set:
0 0 0 0
0 0 0 0
1 0 0 0
1 0 0 0
Then we set the flag row and column to 0's:
0 0 0 0 0
0
0
0
0
Then we have our final output:
0 0 0 0 0
0 0 0 0 0
0 0 0 0 0
1 0 0 0 0
1 0 0 0 0
This would obviously be done in-place, I just separated it out visually for clarity.
I have written C++ implementation with helpful answer of Natalya Ginzburg.
Just leaving it here in case that it could be useful for somebody.
#include <stdio.h>
#include <math.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include <unistd.h>
class Matrix {
public:
Matrix(int n):
side(n),
stride( round(n/8+1) ),
is0RowGood(true),
is0ColGood(true) {
printf("%d %d\n", side, stride);
data = new char[stride*side];
memset(data, 0, stride*side*sizeof(char) );
if( !data ) {
printf("alloc problem\n");
exit(1);
}
fill();
print();
}
~Matrix() {
if(data)
delete data;
}
void process() {
for( int j = 0; j < side; ++j ) {
if(getEl(0, j) == false) {
is0RowGood = false;
break;
}
}
for( int i = 0; i < side; ++i ) {
if(getEl(i, 0) == false) {
is0ColGood = false;
break;
}
}
for( int i = 1; i < side; ++i ) {
for( int j = 1; j < side; ++j ) {
if(!getEl(i,j)) {
setEl(i,0, false);
break;
}
}
}
for( int j = 1; j < side; ++j ) {
for( int i = 1; i < side; ++i ) {
if(!getEl(j,i)) {
setEl(0, i, false);
break;
}
}
}
// nullify now
for( int i = 1; i < side; ++i ) {
for( int j = 1; j < side; ++j ) {
if( !getEl(0,j) || !getEl(i,0) )
{
crossRow(i);
crossCol(j);
}
}
}
if(!is0RowGood)
crossRow(0);
if(!is0ColGood)
crossCol(0);
printf("--\n");
print();
}
private:
void crossRow(int x) {
for(int i = 0; i < side; ++i ) {
setEl(x, i, false);
}
}
void crossCol(int x) {
for(int i = 0; i < side; ++i ) {
setEl(i, x, false);
}
}
void print() {
for( int i = 0; i < side; ++i ) {
for( int j = 0; j < side; ++j ) {
printf(" %d ", getEl(i,j));
}
printf("\n");
}
}
void fill() {
for( int i = 0; i < side; ++i ) {
for( int j = 0; j < side; ++j ) {
usleep(15);
setEl(i, j, (rand() % 30 == 0) ? 0 : 1);
}
}
}
bool getEl(int i, int j) {
int offset = trunc(i/8) + j*stride;
char byte = data[offset];
return byte & static_cast<char>(pow(2, i%8));
}
bool setEl(int i, int j, bool val) {
int offset = trunc(i/8) + j*stride;
if(val)
data[offset] |= static_cast<char>(pow(2, i%8));
else
data[offset] &= static_cast<char>(255-pow(2, i%8));
}
bool is0RowGood;
bool is0ColGood;
char* data;
int side;
int stride;
};
int
main( int argc,
const char** argv ) {
if(argc < 2) {
printf("give n as arg\n");
exit(1);
}
time_t t;
if(argc == 3)
t = atoi(argv[2]);
else {
t = time(NULL);
printf("t=%d",t);
}
srand (t);
int n = atoi( argv[1] );
printf("n=%d\n",n);
Matrix m(n);
m.process();
}
If I enter the numbers:
3 10
7 6
5 5
4 5
the output is : 9. OK — that's the correct value. But if I enter:
10 25
3 5
3 5
3 5
3 5
3 5
3 5
3 5
3 5
3 5
3 5
the correct output should be: 15 but I receive 2005985278.
What's the problem in this code?
#include<stdio.h>
#include<stdlib.h>
#define MA 29
int max(int a, int b) {
return (a > b)? a : b;
}
int knapsack(int W, int P[], int V[], int N)
{
int i, w;
int K[N+1][W+1];
for (i = 0; i <= N; i++)
{
for (w = 1; w <= W; w++)
{
if (i==0 || w==0)
K[i][w] = 0;
else if (P[i-1] <= w)
K[i][w] = max(V[i-1] + K[i-1][w-P[i-1]], K[i-1][w]);
else
K[i][w] = K[i-1][w];
}
}
return K[N][W];
}
int main()
{
int N,W,i;// N: Quantidade de Objetos - W: Capacidade da Mochila; i: interação
int Val=1;//V: Valor;
int Pes=1;//P: Peso;
do{
scanf("%d %d",&N,&W);//ler N e W
for (i=1;i<=N;i++) // iteração
scanf("%d %d",&Val,&Pes);//ler V
//ler P
int V[]={Val};//declaração do vetor V e recebendo Val do scanf
int P[]={Pes};//declaração do vetor P e recebendo Pes do scanf
printf("%d",knapsack(W, P, V, N));
printf("\n");
}while(N!=0 && W!=0);
return 0;
}
I need to enter the number of items N and the capacity W:
When I enter N = 1, W - 7 and the objects P = 4, V = 5 the output is 4.
If I enter other values such as N = 10, W = 25 and P = 3 3 3 3 3 3 3 3 3 3, V = 5 5 5 5 5 5 5 5 5 5, I receive 2005985278 instead of 15.
Please what's the error in my code?
Now my code is this but I receive the erro in my output:
3 10
7 6
5 5
4 5
1 7
4 5
the correct output is : 9 and 4 and i received 7 and 0;
in this case how may i add a end the programm when enter N==0 && W==0?
#include<stdio.h>
#include<stdlib.h>
#define MA 29
int max(int a, int b) {
return (a > b)? a : b;
}
int knapsack(int W, int P[], int V[], int N)
{
int i, w;//interação;
int K[N+1][W+1];//declaração de K recebendo o valor de N e W +1;
for (i = 0; i <=N; i++) // para i=0 i< = N incrementa i;
{
for (w = 0; w <= W; w++)
{
if (i==0 || w==0)
K[i][w] = 0;
else if (P[i-1] <= w)
K[i][w] = max(V[i-1] + K[i-1][w-P[i-1]], K[i-1][w]);
else
K[i][w] = K[i-1][w];
}
}
return K[N][W];
}
int main()
{
int N,W,i;// N: Quantidade de Objetos - W: Capacidade da Mochila; i: interação
//P: Peso;
while (scanf("%d %d", &N, &W) == 2)
{
int V[N];
int P[N];
for (i = 1; i <= N; i++)
if (scanf("%d %d", &V[i], &P[i]) != 2)
break;
printf("%d\n", knapsack(W, P, V, N));
}
}
Your problem is that you are allocating arrays of size 1 and then trying to access 10 elements in those arrays. C won't stop you trying, but it will usually give you the wrong answer.
Existing code:
do{
scanf("%d %d",&N,&W); // Should test for success and terminate loop on failure
for (i=1;i<=N;i++)
scanf("%d %d",&Val,&Pes); // Should check for success; should store values
int V[]={Val}; // V is an array with one entry, the last value entered as Val.
int P[]={Pes}; // P is an array with one entry, the last value entered as Pes.
printf("%d",knapsack(W, P, V, N));
printf("\n");
} while (N!=0 && W!=0);
C99 code:
while (scanf("%d %d", &N, &W) == 2)
{
int V[N];
int P[N];
for (i = 1; i <= N; i++)
if (scanf("%d %d", &V[i], &P[i]) != 2)
break;
printf("%d\n", knapsack(W, P, V, N));
}
Note that if you'd printed the inputs to your knapsack() function, either in the calling code or in the function itself, you'd have seen the trouble very quickly. It is a powerful technique to print your input data after you've finished reading it. Note that printing it while you're reading can mask problems that printing after you've finished reading will reveal.
Clearly, if your knapsack algorithm is incorrect, you'll still get wrong answers; I've not reviewed that and have no particular plans to do so. However, you should be getting the correct input data, which improves enormously the chances of getting the right output.