コース
39237 ワード
オンライン講座ごとに選手講座があり、選手講座のある講座は選手講座を先に聞いてからしか受講できません.
共聴
N
門課.すべてのコース番号は1
からN
までです.N = 3
では、3
号課の先修課が1
号課と2
号課に先修課がないと仮定する.この場合、
1
次講座までの最小時間は30時間、2
次講座までの最小時間は20時間、1
次講座までの最小時間は70時間である.2
授業情報があれば、3
授業にかかる最短時間をそれぞれ出力するプログラムを作成してください.入力条件
1行目は東彬が聞く授業数
N
(1≦N≦500)を与えた.次の
N
行では、各授業の授業時間と受講時に最初に聞く授業番号は自然数で表され、各自然数はスペースで区切られています.各課の番号は1から
N
までで構成され、各行はN
で終了する.しゅつりょくじょうけん
N
受講に必要な最小時間を行ごとに出力します.1.位相整列アルゴリズムを用いて解く
from collections import deque
import copy
v = int(input())
#모든 진입차수 0으로 초기화
indegree = [0] * (v + 1)
graph = [[] for i in range(v + 1)]
#각 강의 시간 0으로 초기화
time = [0] * (v + 1)
for i in range(1, v + 1):
data = list(map(int, input().split()))
time[i] = data[0] #첫 번째 수는 시간 정보
for x in data[1:-1]:
indegree[i] += 1 #진입차수 증가
graph[x].append(i)
def topology_sort():
#수행 결과를 담을 리스트
result = copy.deepcopy(time)
q = deque()
#처음 시작은 진입차수가 0인 노드를 큐에 삽입
for i in range(1, v + 1):
if indegree[i] == 0:
q.append(i)
#큐가 빌 때까지 반복
while q:
#큐에서 원소 꺼내기
now = q.popleft()
for i in graph[now]:
result[i] = max(result[i], result[now] + time[i]) #현재보다 강의 시간이 오래걸리는 경우 시간 값을 저장
indegree[i] -= 1 #진입차수 감소
#새롭게 진입차수가 0이 되는 노드를 큐에 삽입
if indegree[i] == 0:
q.append(i)
for i in range(1, v + 1):
print(result[i])
topology_sort()
各ノードの隣接ノードを確認した場合、隣接ノードの提供時間が現在よりも長いことが判明した場合、結果テーブルを更新することで、より長い時間値を保存することで答えを得ることができます.
最終的には,各科目の受講最小時間を
-1
List変数に計上する.最初に、各レッスンの時間は
N
list変数に含まれ、位相ソート関数の初期部分でresult
関数を使用してtime
list変数の値をコピーし、deepcopy()
list変数の値に設定します.time
関数を使用します.単純な代入操作で値が変更された場合に問題が発生する可能性があります.|リストの値をコピーする必要がある場合はresult
関数を使用します.2.C++コード
#include <bits/stdc++.h>
using namespace std;
// 노드의 개수(V)
int v;
// 모든 노드에 대한 진입차수는 0으로 초기화
int indegree[501];
// 각 노드에 연결된 간선 정보를 담기 위한 연결 리스트 초기화
vector<int> graph[501];
// 각 강의 시간을 0으로 초기화
int times[501];
// 위상 정렬 함수
void topologySort() {
vector<int> result(501); // 알고리즘 수행 결과를 담을 리스트
for (int i = 1; i <= v; i++) {
result[i] = times[i];
}
queue<int> q; // 큐 라이브러리 사용
// 처음 시작할 때는 진입차수가 0인 노드를 큐에 삽입
for (int i = 1; i <= v; i++) {
if (indegree[i] == 0) {
q.push(i);
}
}
// 큐가 빌 때까지 반복
while (!q.empty()) {
// 큐에서 원소 꺼내기
int now = q.front();
q.pop();
// 해당 원소와 연결된 노드들의 진입차수에서 1 빼기
for (int i = 0; i < graph[now].size(); i++) {
result[graph[now][i]] = max(result[graph[now][i]], result[now] + times[graph[now][i]]);
indegree[graph[now][i]] -= 1;
// 새롭게 진입차수가 0이 되는 노드를 큐에 삽입
if (indegree[graph[now][i]] == 0) {
q.push(graph[now][i]);
}
}
}
// 위상 정렬을 수행한 결과 출력
for (int i = 1; i <= v; i++) {
cout << result[i] << '\n';
}
}
int main(void) {
cin >> v;
// 방향 그래프의 모든 간선 정보를 입력받기
for (int i = 1; i <= v; i++) {
// 첫 번째 수는 시간 정보를 담고 있음
int x;
cin >> x;
times[i] = x;
// 해당 강의를 듣기 위해 먼저 들어야 하는 강의들의 번호 입력
while (true) {
cin >> x;
if (x == -1) break;
indegree[i] += 1;
graph[x].push_back(i);
}
}
topologySort();
}
3.Javaコード
import java.util.*;
public class Main {
// 노드의 개수(V)
public static int v;
// 모든 노드에 대한 진입차수는 0으로 초기화
public static int[] indegree = new int[501];
// 각 노드에 연결된 간선 정보를 담기 위한 연결 리스트 초기화
public static ArrayList<ArrayList<Integer>> graph = new ArrayList<ArrayList<Integer>>();
// 각 강의 시간을 0으로 초기화
public static int[] times = new int[501];
// 위상 정렬 함수
public static void topologySort() {
int[] result = new int[501]; // 알고리즘 수행 결과를 담을 배열
for (int i = 1; i <= v; i++) {
result[i] = times[i];
}
Queue<Integer> q = new LinkedList<>(); // 큐 라이브러리 사용
// 처음 시작할 때는 진입차수가 0인 노드를 큐에 삽입
for (int i = 1; i <= v; i++) {
if (indegree[i] == 0) {
q.offer(i);
}
}
// 큐가 빌 때까지 반복
while (!q.isEmpty()) {
// 큐에서 원소 꺼내기
int now = q.poll();
// 해당 원소와 연결된 노드들의 진입차수에서 1 빼기
for (int i = 0; i < graph.get(now).size(); i++) {
result[graph.get(now).get(i)] = Math.max(result[graph.get(now).get(i)], result[now] + times[graph.get(now).get(i)]);
indegree[graph.get(now).get(i)] -= 1;
// 새롭게 진입차수가 0이 되는 노드를 큐에 삽입
if (indegree[graph.get(now).get(i)] == 0) {
q.offer(graph.get(now).get(i));
}
}
}
// 위상 정렬을 수행한 결과 출력
for (int i = 1; i <= v; i++) {
System.out.println(result[i]);
}
}
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
v = sc.nextInt();
// 그래프 초기화
for (int i = 0; i <= v; i++) {
graph.add(new ArrayList<Integer>());
}
// 방향 그래프의 모든 간선 정보를 입력받기
for (int i = 1; i <= v; i++) {
// 첫 번째 수는 시간 정보를 담고 있음
int x = sc.nextInt();
times[i] = x;
// 해당 강의를 듣기 위해 먼저 들어야 하는 강의들의 번호 입력
while (true) {
x = sc.nextInt();
if (x == -1) break;
indegree[i] += 1;
graph.get(x).add(i);
}
}
topologySort();
}
}
Reference
この問題について(コース), 我々は、より多くの情報をここで見つけました https://velog.io/@corone_hi/115.-커리큘럼テキストは自由に共有またはコピーできます。ただし、このドキュメントのURLは参考URLとして残しておいてください。
Collection and Share based on the CC Protocol