To pick a meeting date, n people were asked which of the next m days they are free.
The first line gives the number of people n and the number of days m, separated by one space.
Each of the next n lines gives one person's answer, starting with person 1, as a string of length m.
The k-th character is an uppercase O if that person is free on day k, and an uppercase X if not.
The number of shared free days of persons i and j is the number of days on which both are O.
On lines 1 to n, line i must hold, for j = 1 to n, the number of shared free days of i and j, separated by single spaces.
When i and j are the same, write that person's own number of free days (the count of O).
On the last line print the numbers i and j (i < j) of the pair of different people with the most shared free days, separated by one space.
If several pairs tie, print the one with the smallest i, and among those the smallest j.
If every pair shares 0 days, print 1 2.
Input
2 ≤ n ≤ 100, 1 ≤ m ≤ 100, each answer is a string of length m made only of uppercase O and X
Output
n lines: the n × n table / last line: the numbers of the two people with the most shared free days
Example 1 · stdin
4 5
OOXOX
XOOOX
OOOOO
XXXXO
stdout
3 2 3 0
2 3 3 0
3 3 5 1
0 0 1 1
1 3
Example 2 · stdin
2 3
OXO
XOX
stdout
2 0
0 1
1 2
main.py
Error List00F8 ↓ · ⇧F8 ↑
Input (stdin)
When you run, these lines are fed to input()/stdin in order (the program doesn't stop to ask).
$ Ready
Open this on a computer to write and run code. On mobile you can read the problem and the solutions.
In other languagesShow solutions by language · 8 languages
This is a triple loop: person i, person j, day k. The loop headers are Python for i in range(n):, JS/TS/Java/C#/C/C++ for (int i = 0; i < n; i++) (let in JS/TS) and Craykon for (i = 0; i < n; i++). The most common mistake is putting the counter count = 0 outside the j loop. Then it is not reset when the pair changes, and the previous pairs' counts pile up. Reset it where the thing being counted changes, right inside the j loop. In C, if you declare the loop variables at the top of the function and leave the start of the inner for empty (for (; j < n; j++)), j never starts over and only the first person is examined. Set it fresh each time, as in for (int j = i + 1; ...). Building the table differs by language too. Python [[0] * n] * n points to one and the same row n times, so changing one cell changes that cell in every row; use [[0] * n for _ in range(n)] to make a new row each time. JS/TS has the same problem with new Array(n).fill(new Array(n).fill(0)), so use Array.from({ length: n }, () => new Array(n).fill(0)). Java new int[n][n], C# new int[n, n], C int common[100][100] and C++ std::vector<std::vector<int>>(n, std::vector<int>(n)) create every cell separately. Craykon adds NewList(n, 0) for each row in a loop. Reading a character is rows[i][k] in Python, JS, TS, C#, C, C++ and Craykon, and rows[i].charAt(k) in Java. Since (i, j) and (j, i) hold the same value, counting only j ≥ i and storing into both cells cuts the work about in half. When searching for the best pair, start j at i + 1 so you never choose a cell paired with itself (the diagonal), and loop in order replacing only on > so the earlier pair stays on a tie. Add 1 to the array indexes when printing the numbers.
Pythonmain.py · 23 lines
n, m = map(int, input().split())rows = [input() for _ in range(n)]# common[i][j]: i와 j가 둘 다 비는 날의 수. (i, j)와 (j, i)는 같으니 j >= i만 세고 거울처럼 채운다common = [[0] * n for _ in range(n)]for i in range(n): for j in range(i, n): count = 0 # 쌍마다 새로 센다 for k in range(m): if rows[i][k] == "O" and rows[j][k] == "O": count += 1 common[i][j] = common[j][i] = countfor row in common: print(" ".join(map(str, row)))# 서로 다른 두 사람만: j는 i + 1부터. 차례대로 돌며 >로 바꾸면 같을 때 앞의 쌍이 남는다best_i, best_j = 0, 1for i in range(n): for j in range(i + 1, n): if common[i][j] > common[best_i][best_j]: best_i, best_j = i, jprint(best_i + 1, best_j + 1)
JavaScriptmain.js · 29 lines
const lines = require("fs").readFileSync(0, "utf8").split("\n");const [n, m] = lines[0].trim().split(/\s+/).map(Number);const rows = lines.slice(1, 1 + n).map((s) => s.trim());// common[i][j]: i와 j가 둘 다 비는 날의 수. j >= i만 세고 거울처럼 채운다const common = Array.from({ length: n }, () => new Array(n).fill(0));for (let i = 0; i < n; i++) { for (let j = i; j < n; j++) { let count = 0; // 쌍마다 새로 센다 for (let k = 0; k < m; k++) { if (rows[i][k] === "O" && rows[j][k] === "O") count++; } common[i][j] = common[j][i] = count; }}const out = common.map((row) => row.join(" "));let bi = 0;let bj = 1;for (let i = 0; i < n; i++) { for (let j = i + 1; j < n; j++) { if (common[i][j] > common[bi][bj]) { bi = i; bj = j; } }}out.push(`${bi + 1} ${bj + 1}`);console.log(out.join("\n"));
TypeScriptmain.ts · 30 lines
import { readFileSync } from "node:fs";const lines: string[] = readFileSync(0, "utf8").split("\n");const [n, m] = lines[0].trim().split(/\s+/).map(Number);const rows: string[] = lines.slice(1, 1 + n).map((s) => s.trim());// common[i][j]: i와 j가 둘 다 비는 날의 수. j >= i만 세고 거울처럼 채운다const common: number[][] = Array.from({ length: n }, () => new Array<number>(n).fill(0));for (let i = 0; i < n; i++) { for (let j = i; j < n; j++) { let count = 0; // 쌍마다 새로 센다 for (let k = 0; k < m; k++) { if (rows[i][k] === "O" && rows[j][k] === "O") count++; } common[i][j] = common[j][i] = count; }}const out: string[] = common.map((row) => row.join(" "));let bi = 0;let bj = 1;for (let i = 0; i < n; i++) { for (let j = i + 1; j < n; j++) { if (common[i][j] > common[bi][bj]) { bi = i; bj = j; } }}out.push(`${bi + 1} ${bj + 1}`);console.log(out.join("\n"));
JavaMain.java · 46 lines
import java.io.BufferedReader;import java.io.IOException;import java.io.InputStreamReader;import java.util.StringTokenizer;public class Main { public static void main(String[] args) throws IOException { BufferedReader in = new BufferedReader(new InputStreamReader(System.in)); StringTokenizer st = new StringTokenizer(in.readLine()); int n = Integer.parseInt(st.nextToken()), m = Integer.parseInt(st.nextToken()); String[] rows = new String[n]; for (int i = 0; i < n; i++) rows[i] = in.readLine().trim(); // common[i][j]: i와 j가 둘 다 비는 날의 수. j >= i만 세고 거울처럼 채운다 int[][] common = new int[n][n]; for (int i = 0; i < n; i++) { for (int j = i; j < n; j++) { int count = 0; // 쌍마다 새로 센다 for (int k = 0; k < m; k++) { if (rows[i].charAt(k) == 'O' && rows[j].charAt(k) == 'O') count++; } common[i][j] = common[j][i] = count; } } StringBuilder out = new StringBuilder(); for (int i = 0; i < n; i++) { for (int j = 0; j < n; j++) { if (j > 0) out.append(' '); out.append(common[i][j]); } out.append('\n'); } int bi = 0, bj = 1; for (int i = 0; i < n; i++) { for (int j = i + 1; j < n; j++) { if (common[i][j] > common[bi][bj]) { bi = i; bj = j; } } } out.append(bi + 1).append(' ').append(bj + 1).append('\n'); System.out.print(out); }}
C#Main.cs · 53 lines
using System;using System.Text;class Program{ static void Main() { string[] nm = Console.ReadLine().Split(' ', StringSplitOptions.RemoveEmptyEntries); int n = int.Parse(nm[0]), m = int.Parse(nm[1]); var rows = new string[n]; for (int i = 0; i < n; i++) rows[i] = Console.ReadLine().Trim(); // common[i, j]: i와 j가 둘 다 비는 날의 수. j >= i만 세고 거울처럼 채운다 var common = new int[n, n]; for (int i = 0; i < n; i++) { for (int j = i; j < n; j++) { int count = 0; // 쌍마다 새로 센다 for (int k = 0; k < m; k++) { if (rows[i][k] == 'O' && rows[j][k] == 'O') count++; } common[i, j] = common[j, i] = count; } } var out_ = new StringBuilder(); for (int i = 0; i < n; i++) { for (int j = 0; j < n; j++) { if (j > 0) out_.Append(' '); out_.Append(common[i, j]); } out_.Append('\n'); } int bi = 0, bj = 1; for (int i = 0; i < n; i++) { for (int j = i + 1; j < n; j++) { if (common[i, j] > common[bi, bj]) { bi = i; bj = j; } } } out_.Append(bi + 1).Append(' ').Append(bj + 1).Append('\n'); Console.Write(out_); }}
C++main.cpp · 38 lines
#include <iostream>#include <string>#include <vector>int main() { std::ios::sync_with_stdio(false); int n, m; std::cin >> n >> m; std::vector<std::string> rows(n); for (auto& r : rows) std::cin >> r; // common[i][j]: i와 j가 둘 다 비는 날의 수. j >= i만 세고 거울처럼 채운다 std::vector<std::vector<int>> common(n, std::vector<int>(n, 0)); for (int i = 0; i < n; i++) { for (int j = i; j < n; j++) { int count = 0; // 쌍마다 새로 센다 for (int k = 0; k < m; k++) { if (rows[i][k] == 'O' && rows[j][k] == 'O') count++; } common[i][j] = common[j][i] = count; } } for (int i = 0; i < n; i++) { for (int j = 0; j < n; j++) std::cout << (j ? " " : "") << common[i][j]; std::cout << '\n'; } int bi = 0, bj = 1; for (int i = 0; i < n; i++) { for (int j = i + 1; j < n; j++) { if (common[i][j] > common[bi][bj]) { bi = i; bj = j; } } } std::cout << bi + 1 << ' ' << bj + 1 << '\n';}
Cmain.c · 37 lines
#include <stdio.h>static char rows[100][101];static int common[100][100];int main(void) { int n, m; scanf("%d %d", &n, &m); for (int i = 0; i < n; i++) scanf("%100s", rows[i]); /* common[i][j]: i와 j가 둘 다 비는 날의 수. j >= i만 세고 거울처럼 채운다 */ for (int i = 0; i < n; i++) { for (int j = i; j < n; j++) { int count = 0; /* 쌍마다 새로 센다 */ for (int k = 0; k < m; k++) { if (rows[i][k] == 'O' && rows[j][k] == 'O') count++; } common[i][j] = common[j][i] = count; } } for (int i = 0; i < n; i++) { for (int j = 0; j < n; j++) printf(j ? " %d" : "%d", common[i][j]); printf("\n"); } int bi = 0, bj = 1; for (int i = 0; i < n; i++) { for (int j = i + 1; j < n; j++) { if (common[i][j] > common[bi][bj]) { bi = i; bj = j; } } } printf("%d %d\n", bi + 1, bj + 1); return 0;}
Craykonmain.cray · 50 lines
nm = Console.ReadNumbers();n = nm[0];m = nm[1];rows = [];for (i = 0; i < n; i++){ rows.Add(Console.ReadLine().Trim());}// common[i][j]: i와 j가 둘 다 비는 날의 수. j >= i만 세고 거울처럼 채운다common = [];for (i = 0; i < n; i++){ common.Add(NewList(n, 0));}for (i = 0; i < n; i++){ for (j = i; j < n; j++) { count = 0; // 쌍마다 새로 센다 for (k = 0; k < m; k++) { if (rows[i][k] == "O" && rows[j][k] == "O") { count++; } } common[i][j] = count; common[j][i] = count; }}for (i = 0; i < n; i++){ Console.WriteLine(common[i].Join(" "));}bi = 0;bj = 1;for (i = 0; i < n; i++){ for (j = i + 1; j < n; j++) { if (common[i][j] > common[bi][bj]) { bi = i; bj = j; } }}Console.WriteLine(bi + 1 + " " + (bj + 1));