POJ 2965 The Pilots Brothers' refrigerator

http://poj.org/problem?id=2965

Method 1:

I changed it according to 1753. I enumerated directly from 0 to 16. Some redundant code that does not affect the operation is not deleted

If you don't understand, you can take a look at the solution of 1753: https://www.cnblogs.com/dyhaohaoxuexi/p/10920790.html

#include <stdio.h>
#include <stdlib.h>
#include <iostream>
#include <string.h>

using namespace std;

int flag=0,ms[4][4];

void change(int newm[][4],int *b,int m)
{
    int i;
    for(i=0;i<m;i++)
    {
        int t=b[i];
        int tx=b[i]/4;
        int ty=b[i]%4;
        int j=0;
        for(j=0;j<4;j++)
        newm[tx][j]=!newm[tx][j];
        for(j=0;j<4;j++)
        newm[j][ty]=!newm[j][ty];
        newm[tx][ty]=!newm[tx][ty];   //You have to remember to turn it over again
    }
}

int panduan(int newm[][4],int *b,int m)
{
    int i,j;
    for(i=0;i<4;i++)
    for(j=0;j<4;j++)
    if(newm[i][j]!=1)
    {
        return 0;
    }
    cout<<m<<endl;
    for(i=0;i<m;i++)
    {
        cout<<b[i]/4+1<<' '<<b[i]%4+1<<endl;
    }
    exit(0);  //Exit directly or there may be redundant scheme output
}

void digui(int *a,int *b,int t,int now,int n,int m)
{
    int i,j;
    if(t==m)
    {
        int newm[4][4];
        for(i=0;i<4;i++)
        for(j=0;j<4;j++)
        newm[i][j]=ms[i][j];
        change(newm,b,m);
        if(panduan(newm,b,m))
        flag=1;
        return;
    }
    else
    {
        for(i=now;i<=n-(m-t);i++)
        {
            b[t]=a[i];
            digui(a,b,t+1,i+1,n,m);
        }
    }
}

int main()
{
    int i,j;
    char m[4][4];
    int a[16]={0,2,3,4,5,6,7,8,9,10,11,12,13,14,15,15};
    int b[16];
    for(i=0;i<4;i++)
    {
        cin>>m[i];
        for(j=0;j<4;j++)
        {
            if(m[i][j]=='-')
            ms[i][j]=1;
            else
            ms[i][j]=0;
        }
    }
    for(i=0;i<=16;i++)
    {
        memset(b,0,sizeof(b));
        digui(a,b,0,0,16,i);
        if(flag==1)
        {
            break;
        }        
    }
}

 

Method 2 (quite ingenious):

I see it here:
https://blog.csdn.net/qq_41552508/article/details/79837582

According to the analysis, it can be concluded that the switch itself and the switches in the same row and column are operated once, and the final result is that only the state of the switch itself changes, and all other switch states are unchanged.

After the strategy is found, we will think that if we carry out the above strategy for all the closed switches once, we can definitely turn on the refrigerator. What we need to do next is to remove some useless and repeated operations.

 

#include <cstdio>
#include <cstring>
#include <string>
#include <iostream>
 
using namespace std;
 
int a[4][4];
 
int main()
{
    /*
    When I want to change a grid in the module, I need to change every grid in the row and column of this grid once
    So without encountering a '+', change all the squares in this grid row once
    Finally, for those cells whose change times are odd, the output is enough 
    */
    for(int i = 0;i < 4;i++)
    {
        string c;
        cin>>c;
        for(int j = 0;j < 4;j++)
        {
            if(c[j] == '+')
            {
                for(int k = 0;k < 4;k++)
                {
                    a[i][k]++;
                    if(k!=i)
                        a[k][j]++;
                }
            }
        }
    }
    int sum = 0; //Record the number of odd points 
    for(int i = 0;i < 4;i++)
    {
        for(int j = 0;j < 4;j++)
        {
            if(a[i][j] % 2 != 0)
            {
                sum++;
            }
        }
    }
    printf("%d\n",sum);
    for(int i = 0;i < 4;i++)
    {
        for(int j = 0;j < 4;j++)
        {
            if(a[i][j] % 2 != 0)
            {
                printf("%d %d\n",i+1,j+1);
            }
        }
    }
    return 0;
}

Tags: PHP

Posted on Mon, 04 Nov 2019 11:22:32 -0500 by New Coder