Skip to content

Commit

Permalink
Merge pull request #227 from pdp-archive/html_corrections
Browse files Browse the repository at this point in the history
Mathjax -> KaTeX και μερικές μικρές αλλαγές στην HTML
  • Loading branch information
Dim131 authored Jan 20, 2024
2 parents 9457ff5 + 19e2030 commit a178e91
Show file tree
Hide file tree
Showing 33 changed files with 61 additions and 41 deletions.
18 changes: 17 additions & 1 deletion _includes/scripts.html
Original file line number Diff line number Diff line change
@@ -1,2 +1,18 @@
<script async src="https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.2/MathJax.js?config=TeX-AMS-MML_HTMLorMML"></script>
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/katex@0.16.9/dist/katex.min.css" integrity="sha384-n8MVd4RsNIU0tAv4ct0nTaAbDJwPJzDEaqSD1odI+WdtXRGWt2kTvGFasHpSy3SV" crossorigin="anonymous">
<script defer src="https://cdn.jsdelivr.net/npm/katex@0.16.9/dist/katex.min.js" integrity="sha384-XjKyOOlGwcjNTAIQHIpgOno0Hl1YQqzUOEleOLALmuqehneUG+vnGctmUb0ZY0l8" crossorigin="anonymous"></script>
<script defer src="https://cdn.jsdelivr.net/npm/katex@0.16.9/dist/contrib/auto-render.min.js" integrity="sha384-+VBxd3r6XgURycqtZ117nYw44OOcIax56Z4dCRWbxyPt0Koah1uHoK0o4+/RRE05" crossorigin="anonymous" ></script>
<script type="text/javascript">// <![CDATA[
document.addEventListener("DOMContentLoaded", function() {
renderMathInElement(document.body, {
delimiters: [
{left: '$$', right: '$$', display: true},
{left: '$', right: '$', display: false},
{left: '\\(', right: '\\)', display: false},
{left: '\\[', right: '\\]', display: true}
],
throwOnError : false
});
});
// ]]>
</script>
<script src="/js/contributors_displayer.js"></script>
2 changes: 1 addition & 1 deletion _layouts/default.html
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
<!doctype html>
<html>
<html lang="el">
<head>
<meta charset="utf-8">
<link rel="stylesheet" href="/css/main.css">
Expand Down
6 changes: 3 additions & 3 deletions _layouts/solution.html
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
<!doctype html>
<!DOCTYPE html>
{% assign contest = site.data.contests[page.contest_url] %}
{% assign task = contest[page.codename] %}
{% if task.stage == "c" %}
Expand All @@ -20,14 +20,14 @@
{% else %}
{% assign contrib_salutation = "Συγγραφέας:" %}
{% endif %}
<html>
<html lang="el">
<head>
<meta charset="utf-8">
<link rel="stylesheet" href="/css/main.css">
<title>{{ title }}</title>
{% include scripts.html %}
</head>
<body>
{% include scripts.html %}
{% include announce_everywhere.html %}
<div class="main-content">
<div style="text-align:right">
Expand Down
4 changes: 2 additions & 2 deletions _layouts/statement.html
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
<!doctype html>
<!DOCTYPE html>
{% assign contest = site.data.contests[page.contest_url] %}
{% assign task = contest[page.codename] %}
{% if task.stage == "c" %}
Expand All @@ -17,7 +17,7 @@
{% assign stage_name = "Καμπ (seniors)" %}
{% endif %}
{% assign title = page.contest | append: " " | append: stage_name | append: "<br>" | append: task.full_name | append: " (" | append: page.codename | append: ")" %}
<html>
<html lang="el">
<head>
<meta charset="utf-8">
<link rel="stylesheet" href="/css/main.css">
Expand Down
2 changes: 1 addition & 1 deletion contests/_22-PDP/c-getout-statement.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ Nα αναπτύξετε ένα πρόγραμμα σε μια από τις γ

## Aρχεία εξόδου

Τα αρχεία εξόδου με το όνομα **getout.out** είναι αρχεία κειμένου με μόνο μία γραμμή που περιέχει μόνο έναν αριθμό: το ελάχιστο πλήθος κινήσεων. Αν δεν είναι δυνατόν να ελευθερωθεί η σειρά $$R$$ για να τοποθετηθεί ο αγωγός, το αποτέλεσμα θα είναι $$1$$.
Τα αρχεία εξόδου με το όνομα **getout.out** είναι αρχεία κειμένου με μόνο μία γραμμή που περιέχει μόνο έναν αριθμό: το ελάχιστο πλήθος κινήσεων. Αν δεν είναι δυνατόν να ελευθερωθεί η σειρά $$R$$ για να τοποθετηθεί ο αγωγός, το αποτέλεσμα θα είναι $$-1$$.

## Παράδειγμα αρχείων εισόδου - εξόδου

Expand Down
2 changes: 1 addition & 1 deletion contests/_23-PDP/c-anneal-statement.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ codename: anneal
| 8 <br> 55 10 80 50 20 40 70 60 | 135 |

*Επεξήγηση Παραδείγματος:*
Παρακάμπτουμε τον $$2$$ο και τον $$5$$ο θάλαμο, και μειώνουμε τη θερμοκρασία του 3ου θαλάμου σε $$55$$, και των θαλάμων $$7$$ και $$8$$ σε $$40$$. Η ακολουθία θερμοκρασιών που προκύπτει είναι $$[55, x, 55, 50, x, 40, 40, 40]$$, όπου το $$x$$ δηλώνει τους θαλάμους που έχουν παρακαμφθεί. Το ενεργειακό κόστος είναι: $$(8055) + (7040) + (6040) = 75$$ για την μείωση της θερμοκρασίας στους θαλάμους $$3$$, $$7$$ και $$8$$ αντίστοιχα, και $$2 \cdot 10 + 2 \cdot 20 = 60$$ για τους θαλάμους $$2$$ και $$5$$, αντίστοιχα, που παρακάμψαμε.
Παρακάμπτουμε τον $$2$$ο και τον $$5$$ο θάλαμο, και μειώνουμε τη θερμοκρασία του 3ου θαλάμου σε $$55$$, και των θαλάμων $$7$$ και $$8$$ σε $$40$$. Η ακολουθία θερμοκρασιών που προκύπτει είναι $$[55, x, 55, 50, x, 40, 40, 40]$$, όπου το $$x$$ δηλώνει τους θαλάμους που έχουν παρακαμφθεί. Το ενεργειακό κόστος είναι: $$(80-55) + (70-40) + (60-40) = 75$$ για την μείωση της θερμοκρασίας στους θαλάμους $$3$$, $$7$$ και $$8$$ αντίστοιχα, και $$2 \cdot 10 + 2 \cdot 20 = 60$$ για τους θαλάμους $$2$$ και $$5$$, αντίστοιχα, που παρακάμψαμε.

## Περιορισμοί

Expand Down
4 changes: 2 additions & 2 deletions contests/_23-PDP/camp_c-restaurants-statement.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,11 @@ layout: statement
codename: restaurants
---

Ως υπεύθυνος δικτύου μιας αλυσίδας εστιατορίων, πρέπει να επιλέξετε πού θα ανοίξουν καταστήματα κατά μήκος της νέας εθνικής οδού. Έχουν προεπιλεγεί $$N$$ υποψήφιες θέσεις και μπορούν να ανοίξουν καταστήματα σε οσεσδήποτε από αυτές. Για κάθε υποψήφια θέση $$1 \leq i \leq N$$ έχει υπολογισθεί το αναμενόμενο κέρδος από το κατάστημα που μπορεί να ανοίξει εκεί, με βάση αν θα ανοίξουν καταστήματα στις γειτονικές θέσεις. Αν δεν ανοίξει κατάστημα σε καμία από τις θέσεις $$i1$$ και $$i+1$$, το αναμενόμενο κέρδος από το κατάστημα στην θέση $$i$$ είναι $$a_i$$, αν ανοίξει κατάστημα σε μία από τις θέσεις $$i1$$ και $$i+1$$, το αναμενόμενο κέρδος είναι $$b_i$$, και αν ανοίξουν καταστήματα και στις δύο θέσεις $$i1$$ και $$i+1$$, το αναμενόμενο κέρδος είναι $$c_i$$ (τα $$c_1$$ και $$c_N$$ δεν ορίζονται, και για κάθε θέση $$i$$, ισχύει ότι $$a_i \geq b_i \geq c_i \geq 0$$). Γράψτε ένα πρόγραμμα που να επιλέγει τις θέσεις όπου πρέπει να ανοίξουν τα καταστήματα μεγιστοποιώντας το κέρδος.
Ως υπεύθυνος δικτύου μιας αλυσίδας εστιατορίων, πρέπει να επιλέξετε πού θα ανοίξουν καταστήματα κατά μήκος της νέας εθνικής οδού. Έχουν προεπιλεγεί $$N$$ υποψήφιες θέσεις και μπορούν να ανοίξουν καταστήματα σε οσεσδήποτε από αυτές. Για κάθε υποψήφια θέση $$1 \leq i \leq N$$ έχει υπολογισθεί το αναμενόμενο κέρδος από το κατάστημα που μπορεί να ανοίξει εκεί, με βάση αν θα ανοίξουν καταστήματα στις γειτονικές θέσεις. Αν δεν ανοίξει κατάστημα σε καμία από τις θέσεις $$i-1$$ και $$i+1$$, το αναμενόμενο κέρδος από το κατάστημα στην θέση $$i$$ είναι $$a_i$$, αν ανοίξει κατάστημα σε μία από τις θέσεις $$i-1$$ και $$i+1$$, το αναμενόμενο κέρδος είναι $$b_i$$, και αν ανοίξουν καταστήματα και στις δύο θέσεις $$i-1$$ και $$i+1$$, το αναμενόμενο κέρδος είναι $$c_i$$ (τα $$c_1$$ και $$c_N$$ δεν ορίζονται, και για κάθε θέση $$i$$, ισχύει ότι $$a_i \geq b_i \geq c_i \geq 0$$). Γράψτε ένα πρόγραμμα που να επιλέγει τις θέσεις όπου πρέπει να ανοίξουν τα καταστήματα μεγιστοποιώντας το κέρδος.

## Αρχεία Εισόδου (restaurants.in):

Η πρώτη γραμμή της εισόδου θα περιέχει το πλήθος των υποψήφιων θέσεων $$N$$. Η δεύτερη γραμμή περιέχει $$N$$ αριθμούς, τις τιμές των $$a_1, \ldots , a_N$$. Η τρίτη γραμμή περιέχει $$N$$ αριθμούς, τις τιμές των $$b_1, \ldots , b_N$$. Τέλος, η τέταρτη γραμμή περιέχει $$N2$$ αριθμούς, τις τιμές των $$c_2, \ldots , c_{N1}$$.
Η πρώτη γραμμή της εισόδου θα περιέχει το πλήθος των υποψήφιων θέσεων $$N$$. Η δεύτερη γραμμή περιέχει $$N$$ αριθμούς, τις τιμές των $$a_1, \ldots , a_N$$. Η τρίτη γραμμή περιέχει $$N$$ αριθμούς, τις τιμές των $$b_1, \ldots , b_N$$. Τέλος, η τέταρτη γραμμή περιέχει $$N-2$$ αριθμούς, τις τιμές των $$c_2, \ldots , c_{N-1}$$.

## Αρχεία Εξόδου (restaurants.out):

Expand Down
2 changes: 1 addition & 1 deletion contests/_25-PDP/camp_c-carmeet-statement.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ layout: statement
codename: carmeet
---

Έστω ένας κυκλικός δρόμος, πάνω στον οποίο βρίσκονται $$N$$ πόλεις, αριθμημένες από $$0$$ μέχρι $$N1$$. Ο δρόμος που τις ενώνει είναι μονόδρομος με κατεύθυνση όπως στο παρακάτω σχήμα.
Έστω ένας κυκλικός δρόμος, πάνω στον οποίο βρίσκονται $$N$$ πόλεις, αριθμημένες από $$0$$ μέχρι $$N-1$$. Ο δρόμος που τις ενώνει είναι μονόδρομος με κατεύθυνση όπως στο παρακάτω σχήμα.

<center>
<img alt="Αναπαράσταση του κυκλικού δρόμου που συνδέει τις N πόλεις" src="/assets/25-pdp-camp-c-carmeet-statement-1.png" width="200px">
Expand Down
6 changes: 3 additions & 3 deletions contests/_27-PDP/c-efimerides-solution.md
Original file line number Diff line number Diff line change
Expand Up @@ -19,13 +19,13 @@ codename: efimerides

## Προσομοίωση με πίνακα

Αντί για set (ή hash set), μπορούμε να χρησιμοποιήσουμε έναν boolean πίνακα $$\textit{seen}$$ με $$N$$ θέσεις, όπου το $$\textit{seen}[i]$$ μας λέει αν είδαμε το $$i$$ στην τελευταία διαδρομή. Για να μπορέσουμε να επαναχρησιμοποιήσουμε τον ίδιο πίνακα στην επόμενη διαδρομή, στο τέλος της κάθε διαδρομής ανατρέχουμε στα στοιχεία που επισκεφθήκαμε και θέτουμε την τιμή σε `false`. Ο κώδικας χρειάζεται τις εξής αλλαγές:
Αντί για set (ή hash set), μπορούμε να χρησιμοποιήσουμε έναν boolean πίνακα $$\texttt{seen}$$ με $$N$$ θέσεις, όπου το $$\texttt{seen}[i]$$ μας λέει αν είδαμε το $$i$$ στην τελευταία διαδρομή. Για να μπορέσουμε να επαναχρησιμοποιήσουμε τον ίδιο πίνακα στην επόμενη διαδρομή, στο τέλος της κάθε διαδρομής ανατρέχουμε στα στοιχεία που επισκεφθήκαμε και θέτουμε την τιμή σε `false`. Ο κώδικας χρειάζεται τις εξής αλλαγές:

{% include code.md solution_name='efimerides_slow_table.cc' start=19 end=34 %}

Ο αλγόριθμος ακόμα χρειάζεται $$\mathcal{O}(N^2)$$ χρόνο, αλλά περνάει δύο παραπάνω testcases από την λύση με το hash set. Μπορείτε να βρείτε ολόκληρο τον κώδικα [εδώ]({% include link_to_source.md solution_name='efimerides_slow_table.cc' %}).

**Σημείωση:** Αν θέλουμε να αποφύγουμε το καθάρισμα του πίνακα $$\textit{seen}$$, μπορούμε να κρατάμε έναν ακέραιο $$\textit{last_visited_with}[i]$$, τη θέση από την οποία είδαμε τελευταία φορά τον $$i$$. Οι αλλαγές είναι οι εξής:
**Σημείωση:** Αν θέλουμε να αποφύγουμε το καθάρισμα του πίνακα $$\texttt{seen}$$, μπορούμε να κρατάμε έναν ακέραιο $$\texttt{last\_visited\_with}[i]$$, τη θέση από την οποία είδαμε τελευταία φορά τον $$i$$. Οι αλλαγές είναι οι εξής:

{% include code.md solution_name='efimerides_slow_table_alt.cc' start=19 end=29 %}

Expand All @@ -49,7 +49,7 @@ codename: efimerides
<img alt="Οι κύκλοι στα δύο παραδείγματα της εκφώνησης." src="/assets/27-c-efimerides-cycles.svg" width="450px">
</center>

Άρα, σε έναν κύκλο από όποιο στοιχείο του και να ξεκινήσουμε, θα επισκεφτούμε τα ίδια στοιχεία και άρα θα οδηγήσουν στο ίδιο άθροισμα. Επομένως, αρκεί να επισκεφθούμε το κάθε στοιχείο μία φορά, δηλαδή ξεκινάμε την διαδρομή αν το $$\textit{seen}[i] = \texttt{false}$$. Ο παρακάτω κώδικας υλοποιεί αυτή τη λύση:
Άρα, σε έναν κύκλο από όποιο στοιχείο του και να ξεκινήσουμε, θα επισκεφτούμε τα ίδια στοιχεία και άρα θα οδηγήσουν στο ίδιο άθροισμα. Επομένως, αρκεί να επισκεφθούμε το κάθε στοιχείο μία φορά, δηλαδή ξεκινάμε την διαδρομή αν το $$\texttt{seen}[i] = \texttt{false}$$. Ο παρακάτω κώδικας υλοποιεί αυτή τη λύση:

{% include code.md solution_name='efimerides_fast.cc' %}

Expand Down
19 changes: 12 additions & 7 deletions contests/_28-PDP/blyk-scrabble1d-solution.md
Original file line number Diff line number Diff line change
Expand Up @@ -74,19 +74,24 @@ int main () {

Παρατηρούμε ότι στον παραπάνω κώδικα υπολογίζουμε πολλές φορές από την αρχή τα αθροίσματα των λέξεων, ενώ αυτά δεν αλλάζουν και εξαρτώνται μόνο από το αρχικό κελί $$s$$ της λέξης. Επομένως, μπορούμε να υπολογίσουμε τα αθροίσματα αυτά στην αρχή του κώδικα και να αποφύγουμε επιπλέον επαναλήψεις στον κώδικα. Ο χώρος που θα χρειαστεί για να αποθηκεύσουμε τα αθροίσματα είναι $$\mathcal{O}(N)$$, δηλαδή όσος χρειάζεται για να αποθηκεύσουμε και τις τιμές του πίνακα. Παρ' όλ' αυτά, δεν χρειάζεται πλέον να κρατάμε τις τιμές του αρχικού πίνακα, καθώς το μόνο που χρειαζόμαστε είναι τα αθροίσματα.

Για να υπολογίσουμε τα αθροίσματα των λέξεων (τα οποία μπορούμε να τα λέμε και Κ-αθροίσματα), αρχικά θα υπολογίσουμε τον πίνακα $$\mathit{sums}[s]$$ που θα κρατάει το άθροισμα των στοιχείων από το κελί $$1$$ ως το κελί $$s$$. Άρα θα έχουμε ότι
Για να υπολογίσουμε τα αθροίσματα των λέξεων (τα οποία μπορούμε να τα λέμε και Κ-αθροίσματα), αρχικά θα υπολογίσουμε τον πίνακα $$\texttt{sums}[s]$$ που θα κρατάει το άθροισμα των στοιχείων από το κελί $$1$$ ως το κελί $$s$$. Άρα θα έχουμε ότι

$$
\mathit{sums}[s] = \sum_{i=1}^{s} P_i = P_1 + P_2 + \dotsb + P_{s-1} + P_s
\texttt{sums}[s] = \sum_{i=1}^{s} P_i = P_1 + P_2 + \dotsb + P_{s-1} + P_s.
$$

Με αυτόν τον πίνακα μπορούμε πολύ εύκολα να υπολογίσουμε το Κ-άθροισμα στη θέση $$s$$

$$
\text{Κ-άθροισμα}[s] = P_s + P_{s+1} + \dotsb + P_{s + K - 1} = \\ = (P_1 + P_2 + \dotsb + P_{s + K - 1}) - (P_1 + P_2 + \dotsb + P_{s - 1}) = \\ = \mathit{sums}[s + K - 1] - \mathit{sums}[s - 1]
\begin{align*}
\text{Κ-άθροισμα}[s]
& = P_s + P_{s+1} + \dotsb + P_{s + K - 1}\\
& = (P_1 + P_2 + \dotsb + P_{s + K - 1}) - (P_1 + P_2 + \dotsb + P_{s - 1}) \\
& = \texttt{sums}[s + K - 1] - \texttt{sums}[s - 1].
\end{align*}
$$

Τα αθροίσματα $$\mathit{sums}[i]$$ μπορούν να υπολογιστούν κατά το διάβασμα του αρχείου, και τα αθροίσματα μπορούν τώρα να υπολογιστούν σε μία γραμμή.
Τα αθροίσματα $$\texttt{sums}[i]$$ μπορούν να υπολογιστούν κατά το διάβασμα του αρχείου, και τα αθροίσματα μπορούν τώρα να υπολογιστούν σε μία γραμμή.

```c++
#include <cstdio>
Expand Down Expand Up @@ -131,11 +136,11 @@ int main () {

## Λύση πολυπλοκότητας $$\mathcal{O}(N)$$

Μια ακόμα παρατήρηση που μπορούμε να κάνουμε, είναι ότι υπολογίζουμε το $$\mathit{maxSum_2}$$ κάθε φορά από την αρχή για κάθε τιμή του $$s_1$$. Όμως, το μέγιστο Κ-άθροισμα $$\mathit{maxSum_2}$$ για τη θέση $$s_1$$ (για κάθε $$s_2 \ge s_1 + K$$) είναι όσο το μέγιστο από τα
* $$\mathit{maxSum_2}$$ για τη θέση $$s_1 + 1$$
Μια ακόμα παρατήρηση που μπορούμε να κάνουμε, είναι ότι υπολογίζουμε το $$\texttt{maxSum2}$$ κάθε φορά από την αρχή για κάθε τιμή του $$s_1$$. Όμως, το μέγιστο Κ-άθροισμα $$\texttt{maxSum2}$$ για τη θέση $$s_1$$ (για κάθε $$s_2 \ge s_1 + K$$) είναι όσο το μέγιστο από τα
* $$\texttt{maxSum2}$$ για τη θέση $$s_1 + 1$$
* το Κ-άθροισμα που ξεκινάει από τη θέση $$s_1 + K$$

Επομένως αν έχουμε υπολογίσει το $$\mathit{maxSum_2}$$ για τη θέση $$s_1 + 1$$, μπορούμε με μία σύγκριση να βρούμε το $$\mathit{maxSum_2}$$ για τη θέση $$s_1$$. Αρκεί να διασχίσουμε τον πίνακα ανάποδα και να κρατάμε την τιμή για το έως τώρα μέγιστο $$\mathit{maxSum_2}$$.
Επομένως αν έχουμε υπολογίσει το $$\texttt{maxSum2}$$ για τη θέση $$s_1 + 1$$, μπορούμε με μία σύγκριση να βρούμε το $$\texttt{maxSum2}$$ για τη θέση $$s_1$$. Αρκεί να διασχίσουμε τον πίνακα ανάποδα και να κρατάμε την τιμή για το έως τώρα μέγιστο $$\texttt{maxSum2}$$.

```c++
#include <cstdio>
Expand Down
Loading

0 comments on commit a178e91

Please sign in to comment.