對於式子(((a^b)^b)^b)……,即a對b進行連續異或時,可以發現有如下規律:
若b為1,式子的值會在每次異或之後取反,因為0^1=1,1^1=0,……
若b為0,式子的值會保持a值不變,因為0^0=0,1^0=1,……
因而這種性質可以利用在poj1830這樣的有關聯的開關問題上:(每個開關只能改變一次)
假設開關1和開關2、3相關聯,且開關1的初始狀態為0,終態為1,。
用1表示該開關被改變過,0表示未被改變。
則開關1到達終態的情況可能有:①只改變開關1 ②改變開關1、2、3
則對應的異或式子為 ①((1^0)^0)=1 ②((1^1)^1)=1。
同樣的對於開關2和開關3可以列出相應的式子,此時將開關是否被操作過設定為變數x1,x2,x3。
列出3條方程組,等式右邊1表示與初始狀態不同,0表示與初始狀態相同。
解的數目即為到達終態的情況數目,每組解對應著乙個開關操作情況。
對於題目的第乙個測試用例列出的異或方程為
①x1^x2^x3=1
②x1^x2^x3=1
③x1^x2^x3=1
可求出自由變數有2個,則情況總數為1<<2=4。
對於求解異或方程組,和普通的加減方程組是一樣的,只需要將加減操作換成異或操作,高斯消元化簡後求出自由變數的數目。
第二個測試用例列出的矩陣為
1 1 0 1 1 1 0 1
1 1 0 0 → 0 0 0 1 可看到第二行為無解的情況。
0 0 1 1 0 0 1 1
#include #include #include using namespace std;
int a[35][35];
int b[35];
int n;
int ans;
void swap(int a,int b)
temp=b[a];
b[a]=b[b];
b[b]=temp;
}void gauss()
}if (!flag) continue;
} for (j=i+1;j<=n-1;j++)
}} for (i=n-1;i>=0;i--)
else if (a[i][i]==0)
ans=ans<<1;
else
}} }
}int main()
memset(a,0,sizeof(a));
for (i=0;i<=n-1;i++)
a[i][i]=1;
while (1)
gauss();
if (ans!=-1)
printf("%d\n",ans);
else
printf("oh,it's impossible~!!\n");
} return 0;
}
異或方程組的高斯消元模板:
//有equ個方程,var個變元。增廣矩陣行數為equ,列數為var+1,分別為0到var
int equ,var;
int a[maxn][maxn]; //增廣矩陣
int x[maxn]; //解集
int free_x[maxn];//用來儲存自由變元(多解列舉自由變元可以使用)
int free_num;//自由變元的個數
//返回值為-1表示無解,為0是唯一解,否則返回自由變元個數
int gauss()
if(a[max_r][col] == 0)
if(max_r != k)
for(int i = k+1;i < equ;i++)}}
for(int i = k;i < equ;i++)//進入此迴圈的條件:本身矩陣行大於列 或者 因為出現自由變元後使得非自由變元數比行數小
if(a[i][col] != 0)//若等號右邊是1則無解,因為等號左邊已經消為0
return -1;//無解
if(k < var) return var-k;//自由變元個數
//唯一解,回代
for(int i = var-1; i >= 0;i--)
return 0;
}
poj 1830 異或方程組
題意 有n個相同的開關,每個開關都與某些開關有著聯絡,每當你開啟或者關閉某個開關的時候,其他的與此開關相關聯的開關也會相應地發生變化,即這些相聯絡的開關的狀態如果原來為開就變為關,如果為關就變為開。你的目標是經過若干次開關操作後使得最後n個開關達到乙個特定的狀態。對於任意乙個開關,最多只能進行一次開...
POJ1830 開關問題(異或方程組)
本作品採用知識共享署名 相同方式共享 4.0 國際許可協議進行許可。有n個相同的開關,每個開關都與某些開關有著聯絡,每當你開啟或者關閉某個開關的時候,其他的與此開關相關聯的開關也會相應地發生變化,即這些相聯絡的開關的狀態如果原來為開就變為關,如果為關就變為開。你的目標是經過若干次開關操作後使得最後n...
POJ 1830 開關問題 高斯消元 異或方程組
自由元有兩種取值而且相互不影響,乘法定理可得 include include include using namespace std define for i,j,k for i j i k i define rep i,j,k for i j iconst int dx const int dy ...