{ }codelper
要素の入れ替えP0312

二人ずつ組んで場所を入れ替える

体操の時間に生徒 n 人が一列に並んでいて、位置の番号は左から 1, 2, …, n である。
一行目に n と s が空白一つで区切って与えられる。
二行目に生徒の背番号 n 個が位置の順に空白一つずつで区切って与えられる。
先生が笛を吹くと、s 番の位置から右へ二人ずつ順に組を作る。
つまり s 番と s+1 番が組、s+2 番と s+3 番が組で、これが列の終わりまで続く。
組になった二人は互いに場所を入れ替える。
組のない生徒はその場にとどまる。
s が 2 のときの 1 番の生徒と、列の終わりに一人残る生徒が、組のない生徒である。
入れ替えたあとの背番号を位置の順に空白一つずつで区切って一行に出力せよ。

入力
1 ≤ n ≤ 100、s は 1 または 2、1 ≤ 背番号 ≤ 999(整数)、背番号は互いに異なる
出力
背番号 n 個を空白一つずつで区切った一行
例 1 · stdin
5 1
10 20 30 40 50
stdout
20 10 40 30 50
例 2 · stdin
5 2
10 20 30 40 50
stdout
10 30 20 50 40
main.py
入力(stdin)

実行すると、これらの行が順に input()・標準入力に渡されます(実行中に入力を求めません)。

$ 準備完了

コードを入力して解くにはパソコンで開いてください。モバイルでは問題と解答を見られます。

ほかの言語では?言語別の解答を見る · 8 言語の解答

二つの要素を入れ替える書き方は言語ごとに違います。
Python a[i], a[i + 1] = a[i + 1], a[i]、JS・TS [a[i], a[i + 1]] = [a[i + 1], a[i]]、C# (a[i], a[i + 1]) = (a[i + 1], a[i])、C++ std::swap(a[i], a[i + 1]) は一行で入れ替えます。
C・Java・Craykon は片方を一時変数に預けて三行で入れ替えます。
一つ目の落とし穴は、一時変数なしで a[i] = a[i + 1]; a[i + 1] = a[i]; と書くことです。
一行目で a[i] の元の値が消えるので、例 1 が 20 20 40 40 50 になります。
二つ目の落とし穴はループの終わりです。
ペアの右側 i + 1 がリストの中になければならないので、条件は i + 1 < n です。
i < n で回すと、一人残った最後の生徒がリストの外と入れ替わります。
例 1 では Python は IndexError で、Craykon は「リストには 0〜4 番しかありません」という内容のメッセージで止まります。
JS はエラーを出さず、存在しない要素の undefined と入れ替えるのでリストが一つ伸び、20 10 40 30 のあとに空白二つと 50 が出ます。
C・C++ は範囲を調べないので、エラーなしに関係のない値を読んでしまうことがあります。
三つ目の落とし穴は番号です。
席の番号 s は 1 から、リストの番号は 0 から数えるので、s − 1 番から始めます。
s をそのまま使うと一つずれ、s を見ずにいつも先頭から始めると例 2 が 20 10 40 30 50 になります。

Pythonmain.py · 6 行
n, s = map(int, input().split())a = list(map(int, input().split()))# 자리 번호 s는 1부터 세므로 목록에서는 s - 1번 칸이다for i in range(s - 1, n - 1, 2):    a[i], a[i + 1] = a[i + 1], a[i]   # 임시 변수 없이 한 줄로 맞바꾼다print(*a)
JavaScriptmain.js · 6 行
const [n, s, ...a] = require("fs").readFileSync(0, "utf8").trim().split(/\s+/).map(Number);// 짝의 오른쪽 칸(i + 1)이 목록 안에 있을 때만 바꾼다for (let i = s - 1; i + 1 < n; i += 2) {  [a[i], a[i + 1]] = [a[i + 1], a[i]];}console.log(a.join(" "));
TypeScriptmain.ts · 7 行
import { readFileSync } from "node:fs";const [n, s, ...a]: number[] = readFileSync(0, "utf8").trim().split(/\s+/).map(Number);// 짝의 오른쪽 칸(i + 1)이 목록 안에 있을 때만 바꾼다for (let i = s - 1; i + 1 < n; i += 2) {  [a[i], a[i + 1]] = [a[i + 1], a[i]];}console.log(a.join(" "));
JavaMain.java · 22 行
import java.util.Scanner; public class Main {    public static void main(String[] args) {        Scanner sc = new Scanner(System.in);        int n = sc.nextInt();        int s = sc.nextInt();        int[] a = new int[n];        for (int i = 0; i < n; i++) a[i] = sc.nextInt();        for (int i = s - 1; i + 1 < n; i += 2) {            int tmp = a[i];      // 한쪽을 먼저 맡겨 둔다            a[i] = a[i + 1];            a[i + 1] = tmp;        }        StringBuilder out = new StringBuilder();        for (int i = 0; i < n; i++) {            if (i > 0) out.append(' ');            out.append(a[i]);        }        System.out.println(out);    }}
C#Main.cs · 17 行
using System; class Program{    static void Main()    {        string[] first = Console.ReadLine().Split(' ', StringSplitOptions.RemoveEmptyEntries);        int n = int.Parse(first[0]);        int s = int.Parse(first[1]);        int[] a = Array.ConvertAll(Console.ReadLine().Split(' ', StringSplitOptions.RemoveEmptyEntries), int.Parse);        for (int i = s - 1; i + 1 < n; i += 2)        {            (a[i], a[i + 1]) = (a[i + 1], a[i]);   // 튜플로 한 줄에 맞바꾼다        }        Console.WriteLine(string.Join(" ", a));    }}
C++main.cpp · 15 行
#include <iostream>#include <utility>#include <vector> int main() {    int n, s;    std::cin >> n >> s;    std::vector<int> a(n);    for (int& x : a) std::cin >> x;    for (int i = s - 1; i + 1 < n; i += 2) {        std::swap(a[i], a[i + 1]);    }    for (int i = 0; i < n; i++) std::cout << (i ? " " : "") << a[i];    std::cout << "\n";}
Cmain.c · 15 行
#include <stdio.h> int main(void) {    int n, s, a[100];    scanf("%d %d", &n, &s);    for (int i = 0; i < n; i++) scanf("%d", &a[i]);    for (int i = s - 1; i + 1 < n; i += 2) {        int tmp = a[i];      /* 한쪽을 먼저 맡겨 둔다 */        a[i] = a[i + 1];        a[i + 1] = tmp;    }    for (int i = 0; i < n; i++) printf(i ? " %d" : "%d", a[i]);    printf("\n");    return 0;}
Craykonmain.cray · 12 行
첫줄 = コンソール.数読み();n = 첫줄[0];s = 첫줄[1];a = コンソール.数読み();繰り返す (i = s - 1; i + 1 < n; i += 2){    // 한쪽을 먼저 임시로 맡겨 둔다    임시 = a[i];    a[i] = a[i + 1];    a[i + 1] = 임시;}コンソール.書く(a);