1. 程式人生 > >開燈和蛇形

開燈和蛇形

first cnblogs ems 輸出 lan size 判斷 return 哪些

競賽初入門,發現題目是真的挺難的,一道題目看下來完全不知道在說什麽,或者是沒頭緒,看了答案之後才慢慢能理解,嘛,一步一步來吧。

  • 開燈問題,有n盞燈,編號為1-n, 第一個人把所有的燈都打開,第二個人按下所有編號為2的倍數的開關(這些燈將被關掉),第三個人按下所有編號為3倍數的開關(其中關掉的燈將被打開,開著的燈將被關閉),以此類推,一共有k個人,問最後有哪些燈開著?輸入n和k,輸出開著的燈的編號,k <= n <= 1000.

樣例輸入:
7 3
樣例輸出:
1 5 6 7

  • 分析:這裏直接用雙重循環模擬操作,開著的關掉,關掉的打開,也就是邏輯或運算,而每次一個人開關的燈也可以用取余運算來解決。值得註意的是,第一個燈打開之後就不會關掉了。並且,輸出的第一個燈的編號前面不能有空格。源代碼如下:

    #include <stdio.h>
    #include <string.h>
    #define maxn 1010
    int a[maxn];
    int main(void)
    {
        int lantern, person, first = 0;
        memset(a, 0, sizeof(a));
    
        scanf("%d%d", &lantern, &person);
        for(int i = 1; i <= person; i++)
            for(int j = 1; j <= lantern; j++)
                if
    (j % i == 0) a[j] = !a[j]; for(int i = 1; i <= lantern; i++)) if(a[i]) { if(first) first = 0; else printf(" "); printf("%d", i); } printf("\n"); return 0; }
  • 蛇形填數:在n * n的方陣裏填入 1, 2, ... n * n,要求填成蛇形。例如 n = 4時方陣為:
    10 11 12 1
    9 16   13  2
    8  15   14 3
    7 6  5 4
    在上面的方陣中,多余的空格知識為了便於觀察規律,不必嚴格輸出, n < = 8.
  • 分析: 這個的話其實不難,模擬一下就好了,先將矩陣(二維數組)都初始化為0(方便做判斷),註意不要越界。且要把第一個數字直接先標記成1。

    #include <stdio.h>
    #define maxn 20
    int a[maxn][maxn];
    int main(void)
    {
        int n, x, y;
        memset(a, 0, sizeof(a));
    
        scanf("%d", &n);
        tot = a[x = 1][y = n - 1] = 1;
        while(tot < n * n)
        {
            while(x + 1 < n && !a[x + 1][y]) a[++x][y] = ++tot;
            while(y - 1 >= 0 && a[x][y - 1]) a[x][--y] = ++tot;
            while(x - 1 >= 0 && !a[x - 1][y]) a[--x][y] = ++tot;
            while(y + 1 < n && !a[x][y + 1]) a[x][++y] = ++tot;
        }
        for(x = 0; x < n; x++)
        {
            for(y = 0; y < n; y++)
            printf("%3d", a[x][y]);
            printf("\n");
        }
        return 0;
    }

以上。大概就是這樣子。

開燈和蛇形