{ }codelper
列表下标P0224

单向公交线路的用时

一条单向行驶的公交线路上有 n 个车站。
第一行给出 n。
第二行按公交车经过的顺序给出 n 个车站名,用空格分开。
车站名互不相同。
第三行按同样的顺序给出公交车从起点出发到达各站所用的时间(分钟),共 n 个,用空格分开。
第一个值是 0,越往后越大。
第四行给出询问的个数 q,接下来 q 行每行给出一个询问,形式为 "A B"。
每个询问表示在 A 站上车、在 B 站下车。
在一行输出经过的站数(B 的顺序减去 A 的顺序)和所用时间(分钟),用一个空格分开。
如果 A 或 B 不在线路上,或者 B 在 A 前面(公交车不会倒着开),输出 -1。
如果 A 和 B 是线路上的同一个车站,输出 "0 0"。
A 和 B 相同但不在线路上时,答案是 -1。

输入
1 ≤ n ≤ 1,000,站名是 1 到 10 个英文小写字母,0 = 第一个时间 < … < 最后一个时间 ≤ 100,000,1 ≤ q ≤ 1,000,询问中的 A、B 也是 1 到 10 个小写字母(可能不在线路上)
输出
q 行,每行是“站数 时间”或 -1
样例 1 · stdin
5
city park school market river
0 4 9 15 22
5
park market
city river
market park
school school
park zoo
stdout
2 11
4 22
-1
0 0
-1
样例 2 · stdin
2
a b
0 100000
3
a b
b a
zoo a
stdout
1 100000
-1
-1
main.py
输入(stdin)

运行时这些行会依次作为 input()/标准输入传入(运行中不会等待输入)。

$ 就绪

请在电脑上打开以编写和运行代码。在手机上可以查看题目和题解。

其他语言怎么写?查看各语言题解 · 8 种语言题解

这道题按名字查出位置(index-of),再用这个位置去读另一个列表的值。
查找方法和找不到时的结果因语言而异。
JS/TS stops.indexOf(a)、Java List.indexOf、C# Array.IndexOf、Craykon stops.查找位置(a) 找不到时返回 -1。
Python list.index 找不到会抛出 ValueError,所以先用 in 检查。
C++ std::find 找不到时返回 end(),C 标准库没有按顺序在数组里查找的函数(bsearch 只用于排好序的数组),要自己用 strcmp 写循环。
陷阱是不检查 -1 就直接当下标用(在 Python 中,是指从自己写的查找函数或 dict.get(a, -1) 得到 -1 的情况)。
在 Python 中 times[-1] 不报错地变成最后一站的时间,得到看似合理的错误答案;JS/TS 的 times[-1] 是 undefined,会输出 NaN。
反过来,用 > 0 判断是否找到,会把位置为 0 的第一站当成不存在。
要用 >= 0 或 != -1 判断。
在 Java 中用 == 比较从输入读入的字符串,即使内容相同也因为是不同对象而找不到。
indexOf 用 equals 比较,所以没问题。
倒着走的询问不要用绝对值回答,而是 -1。

Pythonmain.py · 17 行
n = int(input())stops = input().split()times = list(map(int, input().split()))q = int(input())out = []for _ in range(q):    a, b = input().split()    # list.index는 없으면 ValueError를 내니 먼저 in으로 확인한다    if a not in stops or b not in stops:        out.append("-1")        continue    i, j = stops.index(a), stops.index(b)    if j < i:                       # 버스는 거꾸로 가지 않는다        out.append("-1")    else:        out.append(f"{j - i} {times[j] - times[i]}")   # 같은 번호로 다른 목록을 읽는다print("\n".join(out))
JavaScriptmain.js · 16 行
const lines = require("fs").readFileSync(0, "utf8").split("\n");const stops = lines[1].trim().split(" ");const times = lines[2].trim().split(" ").map(Number);const q = Number(lines[3]);const out = [];for (let t = 0; t < q; t++) {  const [a, b] = lines[4 + t].trim().split(" ");  const i = stops.indexOf(a); // 없으면 -1  const j = stops.indexOf(b);  if (i === -1 || j === -1 || j < i) {    out.push("-1");  } else {    out.push(`${j - i} ${times[j] - times[i]}`);  }}console.log(out.join("\n"));
TypeScriptmain.ts · 17 行
import { readFileSync } from "node:fs";const lines: string[] = readFileSync(0, "utf8").split("\n");const stops: string[] = lines[1].trim().split(" ");const times: number[] = lines[2].trim().split(" ").map(Number);const q: number = Number(lines[3]);const out: string[] = [];for (let t = 0; t < q; t++) {  const [a, b] = lines[4 + t].trim().split(" ");  const i: number = stops.indexOf(a); // 없으면 -1  const j: number = stops.indexOf(b);  if (i === -1 || j === -1 || j < i) {    out.push("-1");  } else {    out.push(`${j - i} ${times[j] - times[i]}`);  }}console.log(out.join("\n"));
JavaMain.java · 25 行
import java.io.BufferedReader;import java.io.IOException;import java.io.InputStreamReader;import java.util.Arrays;import java.util.List; public class Main {    public static void main(String[] args) throws IOException {        BufferedReader in = new BufferedReader(new InputStreamReader(System.in));        in.readLine();        List<String> stops = Arrays.asList(in.readLine().trim().split(" "));        int[] times = Arrays.stream(in.readLine().trim().split(" ")).mapToInt(Integer::parseInt).toArray();        int q = Integer.parseInt(in.readLine().trim());        StringBuilder out = new StringBuilder();        for (int t = 0; t < q; t++) {            String[] p = in.readLine().trim().split(" ");            int i = stops.indexOf(p[0]); // 없으면 -1(문자열 내용으로 비교한다)            int j = stops.indexOf(p[1]);            if (i == -1 || j == -1 || j < i) out.append("-1");            else out.append(j - i).append(' ').append(times[j] - times[i]);            out.append('\n');        }        System.out.print(out);    }}
C#Main.cs · 25 行
using System;using System.Linq;using System.Text; class Program{    static void Main()    {        Console.ReadLine();        string[] stops = Console.ReadLine().Trim().Split(' ');        int[] times = Console.ReadLine().Trim().Split(' ').Select(int.Parse).ToArray();        int q = int.Parse(Console.ReadLine());        var sb = new StringBuilder();        for (int t = 0; t < q; t++)        {            string[] p = Console.ReadLine().Trim().Split(' ');            int i = Array.IndexOf(stops, p[0]); // 없으면 -1, 첫 정류장은 0            int j = Array.IndexOf(stops, p[1]);            if (i < 0 || j < 0 || j < i) sb.Append("-1");            else sb.Append(j - i).Append(' ').Append(times[j] - times[i]);            sb.Append('\n');        }        Console.Write(sb);    }}
C++main.cpp · 28 行
#include <algorithm>#include <iostream>#include <string>#include <vector> int main() {    std::ios::sync_with_stdio(false);    int n, q;    std::cin >> n;    std::vector<std::string> stops(n);    std::vector<int> times(n);    for (auto& s : stops) std::cin >> s;    for (int& x : times) std::cin >> x;    std::cin >> q;    for (int t = 0; t < q; t++) {        std::string a, b;        std::cin >> a >> b;        // std::find는 못 찾으면 end()를 돌려준다(번호로 치면 n)        auto ia = std::find(stops.begin(), stops.end(), a);        auto ib = std::find(stops.begin(), stops.end(), b);        if (ia == stops.end() || ib == stops.end() || ib < ia) {            std::cout << "-1\n";            continue;        }        int i = ia - stops.begin(), j = ib - stops.begin();        std::cout << j - i << " " << times[j] - times[i] << "\n";    }}
Cmain.c · 29 行
#include <stdio.h>#include <string.h> static char stops[1000][11];static int times[1000];static int n; /* 이름이 처음 나오는 번호, 없으면 -1 */int index_of(const char *name) {    for (int i = 0; i < n; i++)        if (strcmp(stops[i], name) == 0) return i;    return -1;} int main(void) {    int q;    char a[11], b[11];    scanf("%d", &n);    for (int i = 0; i < n; i++) scanf("%10s", stops[i]);    for (int i = 0; i < n; i++) scanf("%d", &times[i]);    scanf("%d", &q);    for (int t = 0; t < q; t++) {        scanf("%10s %10s", a, b);        int i = index_of(a), j = index_of(b);        if (i == -1 || j == -1 || j < i) puts("-1");        else printf("%d %d\n", j - i, times[j] - times[i]);    }    return 0;}
Craykonmain.cray · 18 行
控制台.读行();stops = 控制台.读行().去空白().分割(" ");times = 控制台.读数字();q = 控制台.读行().转数字();循环 (t = 0; t < q; t++){    p = 控制台.读行().去空白().分割(" ");    i = stops.查找位置(p[0]); // 없으면 -1    j = stops.查找位置(p[1]);    如果 (i == -1 || j == -1 || j < i)    {        控制台.输出(-1);    }    否则    {        控制台.输出(j - i + " " + (times[j] - times[i]));    }}