Compare commits

..

18 Commits

  1. 30
      app/app.go
  2. 112
      labs/coursework.js
  3. 3
      labs/lab1/desc.json
  4. 21
      labs/lab10/desc.json
  5. 17
      labs/lab10/main.js
  6. 21
      labs/lab11/desc.json
  7. 33
      labs/lab11/main.js
  8. 31
      labs/lab12/desc.json
  9. 60
      labs/lab12/main.js
  10. 6
      labs/lab13/desc.json
  11. 9
      labs/lab13/main.js
  12. 6
      labs/lab14/desc.json
  13. 29
      labs/lab14/main.js
  14. 3
      labs/lab2/desc.json
  15. 3
      labs/lab3/desc.json
  16. 28
      labs/lab4/desc.json
  17. 34
      labs/lab4/main.js
  18. 28
      labs/lab5/desc.json
  19. 31
      labs/lab5/main.js
  20. 21
      labs/lab6/desc.json
  21. 34
      labs/lab6/main.js
  22. 43
      labs/lab7/desc.json
  23. 63
      labs/lab7/main.js
  24. 21
      labs/lab8/desc.json
  25. 30
      labs/lab8/main.js
  26. 21
      labs/lab9/desc.json
  27. 35
      labs/lab9/main.js
  28. 18
      main.go
  29. 2
      models/lab.go
  30. 25
      web/static/styles.css
  31. 26
      web/templates/coursework.html
  32. 1
      web/templates/index.html
  33. 2
      web/templates/lab.html

30
app/app.go

@ -8,6 +8,7 @@ import (
"log"
"net/http"
"net/url"
"strconv"
"git.atik.me/basicweb/models"
)
@ -15,7 +16,7 @@ import (
type App struct {
LabsFS fs.FS
WebFS fs.FS
Labs map[string]models.Lab
Labs map[int]models.Lab
}
func New(labsFS fs.FS, webFS fs.FS) App {
@ -50,17 +51,24 @@ func (a *App) LabPageHandler(writer http.ResponseWriter, request *http.Request)
return
}
number := parsedURL.Query().Get("number")
if number == "" {
strNumber := parsedURL.Query().Get("number")
if strNumber == "" {
writer.WriteHeader(http.StatusNotFound)
writer.Write([]byte("Не указан номер лабораторной работы!"))
return
}
number, err := strconv.Atoi(strNumber)
if err != nil {
writer.WriteHeader(http.StatusNotFound)
writer.Write([]byte("Некорректный номер лабораторной работы!"))
return
}
lab, ok := a.Labs[number]
if !ok || !lab.Complete {
writer.WriteHeader(http.StatusNotFound)
writer.Write([]byte("Лаборатораня работа с номером " + number + " не найдена!"))
writer.Write([]byte("Лаборатораня работа с номером " + strconv.Itoa(number) + " не найдена!"))
return
}
@ -69,9 +77,19 @@ func (a *App) LabPageHandler(writer http.ResponseWriter, request *http.Request)
}
}
func getLabsList(labsFS fs.FS) map[string]models.Lab {
func (a *App) CourseworkPageHandler(writer http.ResponseWriter, request *http.Request) {
cwFile, err := fs.ReadFile(a.WebFS, "templates/coursework.html")
if err != nil {
log.Fatal(err)
}
writer.WriteHeader(http.StatusOK)
writer.Write(cwFile)
}
func getLabsList(labsFS fs.FS) map[int]models.Lab {
var result = make(map[string]models.Lab)
var result = make(map[int]models.Lab)
folders, err := fs.ReadDir(labsFS, "labs")
if err != nil {

112
labs/coursework.js

@ -0,0 +1,112 @@
"use strict";
function main() {
let result = document.getElementById("result");
let arr = document.forms[0].elements[0].value;
arr = arr.trim().split(" ");
let checkResult = arr.some( elem => isNotNumber(elem) );
if (checkResult) {
result.innerHTML = "<p class='fail'>Ошибка: введите только целые числа, разделенные пробелом!</p>";
return;
} else if (arr.length < 2) {
result.innerHTML = "<p class='fail'>Ошибка: введите минимум 2 числа!</p>";
return;
} else {
arr = arr.map( elem => Number(elem) );
}
let graph = createGraph(arr);
let path = findPath(graph);
if (path == undefined) {
result.innerHTML = "<p class='fail'>Результат: путь не найден!</p>";
return;
}
arr[0] = "Start";
arr[arr.length - 1] = "End";
let table = "<table id='table'><tr><th>Метка</th><th>Номер прыжка</th></tr>";
arr.forEach( elem => table += "<tr><td>" + elem + "</td><td></td></tr>" );
table += "</table>";
result.innerHTML = "<p class='success'>Результат: путь найден! Прыжков в пути: " + (path.length - 1) + "</p>" + table;
path.forEach( (elem, index) =>
document.getElementById("table").rows[elem + 1].cells[1].innerHTML = index
);
}
function createGraph(arr) {
let result = [];
// Добавляем узлы берегов
arr.unshift(1);
arr.push(0);
length = arr.length;
arr.forEach( (elem, index) => {
result[index] = {
prev: undefined,
dist: Number.POSITIVE_INFINITY,
visited: false,
childs: []
};
if (elem <= index) {
result[index].childs.push(index - elem);
}
let forwardIndex = elem >= (length - index) ? length - 1 : index + elem;
result[index].childs.push(forwardIndex);
});
return result;
}
function findPath(graph) {
let queue = [];
queue.push(0);
graph[0].dist = 0;
mainLoop: while(queue.length > 0) {
let v = queue.shift()
for (let child of graph[v].childs) {
if (!graph[child].visited) {
queue.push(child)
graph[v].visited = true;
let dist = graph[v].dist + 1;
if ( dist < graph[child].dist ) {
graph[child].prev = v;
graph[child].dist = dist;
}
if (child == graph.length - 1) {
break mainLoop;
}
}
}
}
if (graph[graph.length - 1].dist == Number.POSITIVE_INFINITY) {
return undefined;
}
let path = [];
let index = graph.length - 1;
while (index >= 0) {
path.push(index);
index = graph[index].prev;
}
return path.reverse();
}
function isNotNumber(val) {
return val.replace(/\s/g, '').length === 0 || isNaN(val) || !Number.isInteger(Number(val));
}

3
labs/lab1/desc.json

@ -1,5 +1,5 @@
{
"number": "1",
"number": 1,
"task": "Создайте функцию, которая принимает массив чисел arr и число n. Верните true, если сумма любых двух элементов равна заданному числу. В противном случае верните false.",
"vars": [
[
@ -39,6 +39,5 @@
}
]
],
"scriptpath": "labs/lab1/main.js",
"complete": true
}

21
labs/lab10/desc.json

@ -0,0 +1,21 @@
{
"number": 10,
"task": "Создайте функцию, которая принимает положительное целое число (одно из base2, base8 или base16), преобразует целое число в заданное основание и возвращает строку с использованием рекурсии.",
"vars": [
[
{
"name": "n",
"desc": "Число в двоичной системе",
"data": ""
}
],
[
{
"name": "n",
"desc": "Число в двоичной системе",
"data": "999"
}
]
],
"complete": true
}

17
labs/lab10/main.js

@ -0,0 +1,17 @@
"use strict";
function main(formName) {
let result = document.getElementById("result");
let n = document.forms[formName].elements[0].value;
if ( !/^[01]+$/.test(n) ) {
result.textContent = "Ошибка: n должно содежать только нули и единицы!";
return;
}
result.textContent = "Результат: " + binToDecimal(Number(n));
}
function binToDecimal(n) {
return n == 0 ? 0 : n % 10 + 2 * binToDecimal(Math.trunc(n / 10));
}

21
labs/lab11/desc.json

@ -0,0 +1,21 @@
{
"number": 11,
"task": "Создайте функцию, которая возвращает количество пятниц, 13-го числа в заданном году.",
"vars": [
[
{
"name": "year",
"desc": "Исследуемый год",
"data": ""
}
],
[
{
"name": "year",
"desc": "Исследуемый год",
"data": "2021"
}
]
],
"complete": true
}

33
labs/lab11/main.js

@ -0,0 +1,33 @@
"use strict";
function main(formName) {
let result = document.getElementById("result");
let year = document.forms[formName].elements[0].value;
if (isNotNumber(year)) {
result.textContent = "Ошибка: year не является числом!";
return;
}
if (!Number.isInteger(Number(year))) {
result.textContent = "Ошибка: year должен быть целым!";
return;
}
result.textContent = "Результат: " + countFridays(year);
}
function countFridays(year) {
let result = 0;
for (let month = 1; month <= 12; month++) {
let date = new Date(year, month, 13);
result += date.getDay() == 5 ? 1 : 0;
}
return result;
}
function isNotNumber(val) {
return val.replace(/\s/g, '').length === 0 || isNaN(val);
}

31
labs/lab12/desc.json

@ -0,0 +1,31 @@
{
"number": 12,
"task": "Создавайте функции для класса Calculator, которые могут делать следующее: складывать два числа, вычитать два числа, умножать два числа, делить два числа.",
"vars": [
[
{
"name": "a",
"desc": "Первое число",
"data": ""
},
{
"name": "b",
"desc": "Первое число",
"data": ""
}
],
[
{
"name": "a",
"desc": "Первое число",
"data": "6"
},
{
"name": "b",
"desc": "Первое число",
"data": "2"
}
]
],
"complete": true
}

60
labs/lab12/main.js

@ -0,0 +1,60 @@
"use strict";
function main(formName) {
let result = document.getElementById("result");
let a = document.forms[formName].elements[0].value;
if (isNotNumber(a)) {
result.textContent = "Ошибка: a не является числом!";
return;
} else {
a = Number(a);
}
let b = document.forms[formName].elements[1].value;
if (isNotNumber(b)) {
result.textContent = "Ошибка: b не является числом!";
return;
} else {
b = Number(b);
}
result.textContent = "Результат: " + Calculate(a, b);
}
function Calculate(a, b) {
class Calculator {
constructor(a, b) {
this.a = a;
this.b = b;
}
add() {
return this.a + this.b;
}
subtract() {
return this.a - this.b;
}
multiply() {
return this.a * this.b;
}
devide() {
return this.a / this.b;
}
}
let result;
let calc = new Calculator(a, b);
result = "сложение: " + calc.add();
result += ", вычитание: " + calc.subtract();
result += ", умножение: " + calc.multiply();
result += ", деление: " + calc.devide();
return result;
}
function isNotNumber(val) {
return val.replace(/\s/g, '').length === 0 || isNaN(val);
}

6
labs/lab13/desc.json

@ -0,0 +1,6 @@
{
"number": 13,
"task": "Напишите программу, чтобы получить ширину и высоту окна (каждый раз, когда размер окна изменяется).",
"vars": [],
"complete": true
}

9
labs/lab13/main.js

@ -0,0 +1,9 @@
"use strict";
window.onresize = viewSizes;
viewSizes();
function viewSizes() {
let result = document.getElementById("result");
result.textContent = "Результат: " + window.innerWidth + "x" + window.innerHeight;
}

6
labs/lab14/desc.json

@ -0,0 +1,6 @@
{
"number": 14,
"task": "Вам будет предоставлен набор напитков, каждый из которых является объектом с двумя свойствами: названием и ценой. Создайте функцию с массивом напитков в качестве аргумента и верните объекты напитков, отсортированные по цене в порядке возрастания.",
"vars": [[]],
"complete": true
}

29
labs/lab14/main.js

@ -0,0 +1,29 @@
"use strict";
function main(formName) {
let result = document.getElementById("result");
let arr = [
{name: "Кола", price: 5},
{name: "Вода", price: 1},
{name: "Чай", price: 2},
{name: "Коктейль", price: 10},
{name: "Мохито", price: 8}
];
if (item instanceof Array) {
result.textContent = "Ошибка: arr должен быть массивом!";
return;
}
result.textContent = "Результат: " + sortDrinks(arr);
}
function sortDrinks(arr) {
let result = [];
arr.sort( (first, second) => first.price > second.price ? 1 : -1 );
arr.forEach( elem => result.push(elem.name + " - " + elem.price) );
return result.join(", ");
}

3
labs/lab2/desc.json

@ -1,7 +1,6 @@
{
"number": "2",
"number": 2,
"task": "Подсчитайте общее количество массивов внутри данного массива. Т.к. конвертирование строки в многомерный массив, не самая тривиальная задача, то исходный массив задается внутри кода.\narr = [[1, 2, 3, [1, 2, 3]], [[[]]], 3]",
"vars": [[]],
"scriptpath": "labs/lab2/main.js",
"complete": true
}

3
labs/lab3/desc.json

@ -1,5 +1,5 @@
{
"number": "3",
"number": 3,
"task": "Напишите функцию, которая меняет местами все слова в предложении, начинающиеся с определенной буквы.",
"vars": [
[
@ -39,6 +39,5 @@
}
]
],
"scriptpath": "labs/lab3/main.js",
"complete": true
}

28
labs/lab4/desc.json

@ -0,0 +1,28 @@
{
"number": 4,
"task": "Создайте функцию, которая принимает число в качестве входных данных и возвращает true, если сумма ее цифр имеет ту же четность, что и все число. В противном случае верните false.",
"vars": [
[
{
"name": "n",
"desc": "Исходное число",
"data": ""
}
],
[
{
"name": "n",
"desc": "Исходное число",
"data": "25"
}
],
[
{
"name": "n",
"desc": "Исходное число",
"data": "14"
}
]
],
"complete": true
}

34
labs/lab4/main.js

@ -0,0 +1,34 @@
"use strict";
function main(formName) {
let result = document.getElementById("result");
let n = document.forms[formName].elements[0].value;
if (isNotNumber(n)) {
result.textContent = "Ошибка: n не является числом!";
return;
}
if (!Number.isInteger(Number(n))) {
result.textContent = "Ошибка: проверка четности доступна только для целых чисел!";
return;
}
result.textContent = "Результат: " + checkParity(n);
}
function checkParity(n) {
return Math.abs(n % 2) == getSumOfDigits(n) % 2;
}
function isNotNumber(val) {
return val.replace(/\s/g, '').length === 0 || isNaN(val);
}
function getSumOfDigits(num) {
let result = 0;
for (let char of num) {
result += isNotNumber(char) ? 0 : Number(char);
}
return result;
}

28
labs/lab5/desc.json

@ -0,0 +1,28 @@
{
"number": 5,
"task": "Повторяющийся квадратный корень из числа - это количество раз, которое необходимо применить к функции извлечения квадратного корня, чтобы число было строго меньше 2. Для заданного целого числа вернуть повторяющийся квадратный корень. Вернуть «недействительно», если оно отрицательное.",
"vars": [
[
{
"name": "n",
"desc": "Исходное число",
"data": ""
}
],
[
{
"name": "n",
"desc": "Исходное число",
"data": "8"
}
],
[
{
"name": "n",
"desc": "Исходное число",
"data": "-5"
}
]
],
"complete": true
}

31
labs/lab5/main.js

@ -0,0 +1,31 @@
"use strict";
function main(formName) {
let result = document.getElementById("result");
let n = document.forms[formName].elements[0].value;
if (isNotNumber(n)) {
result.textContent = "Ошибка: n не является числом!";
return;
}
result.textContent = "Результат: " + countRoots(n);
}
function countRoots(n) {
if (n < 0) {
return undefined;
}
let result = 0;
while (n >= 2) {
n = Math.sqrt(n);
result++;
}
return result;
}
function isNotNumber(val) {
return val.replace(/\s/g, '').length === 0 || isNaN(val);
}

21
labs/lab6/desc.json

@ -0,0 +1,21 @@
{
"number": 6,
"task": "Учитывая массив целых чисел, представляющих цвет каждого носка, определите, сколько пар носков совпадающих цветов существует. Например, есть 7 носков цветов [1, 2, 1, 2, 1, 3, 2]. Остается одна пара цвета 1 и одна пара цвета 2. Осталось три нечетных носка, по одному каждого цвета. Количество пар равно 2. Создайте функцию, которая возвращает целое число, представляющее количество подходящих пар доступных носков.",
"vars": [
[
{
"name": "arr",
"desc": "Массив носков",
"data": ""
}
],
[
{
"name": "arr",
"desc": "Массив носков",
"data": "1 2 1 2 1 3 2"
}
]
],
"complete": true
}

34
labs/lab6/main.js

@ -0,0 +1,34 @@
"use strict";
function main(formName) {
let result = document.getElementById("result");
let arr = document.forms[formName].elements[0].value;
arr = arr.trim().split(" ");
let checkResult = arr.some( elem => isNotNumber(elem) );
if (checkResult) {
result.textContent = "Ошибка: arr должен содержать только числа, разделенные пробелом!";
return;
} else {
arr = arr.map( elem => Number(elem) );
}
result.textContent = "Результат: " + countPairs(arr);
}
function countPairs(arr) {
let map = new Map();
for (let num of arr) {
map.set(num, (map.get(num) || 0) + 1);
}
let result = 0;
map.forEach( val => result += Math.trunc(val / 2) );
return result;
}
function isNotNumber(val) {
return val.replace(/\s/g, '').length === 0 || isNaN(val);
}

43
labs/lab7/desc.json

@ -0,0 +1,43 @@
{
"number": 7,
"task": "Создайте функцию, которая возвращает количество чисел палиндрома в указанном диапазоне (включительно). Например, между 8 и 34 имеется 5 палиндромов: 8, 9, 11, 22 и 33. Между 1550 и 1552 годами существует ровно один палиндром: 1551. Т.к. в условии не оговорен случай отрицательных чисел, то такие числа не будут рассматриваться отдельно, т.к. чисел вида '-11-' не существует. При указании в качестве начала диапазона вещественного числа, в список проверяемых чисел попадут только вещественные числа, для которых накладывается дополнительное условие в виде расположения разделительной точки ровно в середине числа.",
"vars": [
[
{
"name": "a",
"desc": "Начало диапазона",
"data": ""
},
{
"name": "b",
"desc": "Конец диапазона",
"data": ""
}
],
[
{
"name": "a",
"desc": "Начало диапазона",
"data": "8"
},
{
"name": "b",
"desc": "Конец диапазона",
"data": "34"
}
],
[
{
"name": "a",
"desc": "Начало диапазона",
"data": "1550"
},
{
"name": "b",
"desc": "Конец диапазона",
"data": "1552"
}
]
],
"complete": true
}

63
labs/lab7/main.js

@ -0,0 +1,63 @@
"use strict";
function main(formName) {
let result = document.getElementById("result");
let a = document.forms[formName].elements[0].value;
if (isNotNumber(a)) {
result.textContent = "Ошибка: a не является числом!";
return;
} else {
a = Number(a);
}
let b = document.forms[formName].elements[1].value;
if (isNotNumber(b)) {
result.textContent = "Ошибка: b не является числом!";
return;
} else {
b = Number(b);
}
if (a > b) {
result.textContent = "Ошибка: a не может быть больше b";
return;
}
result.textContent = "Результат: " + countPalindrome(a, b);
}
function countPalindrome(a, b) {
let result = 0;
let gen = makeRangeIterator(a, b);
for (let num of gen) {
if (isPalindrome(num)) {
result++;
}
}
return result;
}
function isPalindrome(num) {
let strNumber = num.toString();
for (let i = 0; i <= strNumber.length / 2; i++) {
let lastIndex = strNumber.length - 1 -i;
if (strNumber[i] != strNumber[lastIndex]) {
return false;
}
}
return true;
}
function isNotNumber(val) {
return val.replace(/\s/g, '').length === 0 || isNaN(val);
}
function* makeRangeIterator(start, end) {
for (let i = start; i < end; i++) {
yield i;
}
return end;
}

21
labs/lab8/desc.json

@ -0,0 +1,21 @@
{
"number": 8,
"task": "Создайте функцию, которая принимает одну строку в качестве аргумента и возвращает упорядоченный массив, содержащий индексы всех заглавных букв в строке.",
"vars": [
[
{
"name": "s",
"desc": "Разбираемая строка",
"data": ""
}
],
[
{
"name": "s",
"desc": "Разбираемая строка",
"data": "Мама Мыла Раму"
}
]
],
"complete": true
}

30
labs/lab8/main.js

@ -0,0 +1,30 @@
"use strict";
function main(formName) {
let result = document.getElementById("result");
let s = document.forms[formName].elements[0].value;
if (!(typeof s === "string")) {
result.textContent = "Ошибка: s не является строкой!";
return;
}
result.textContent = "Результат: " + countUpperChars(s);
}
function countUpperChars(s) {
let result = [];
let pattern = /^[A-ZА-Я]+$/;
Array.from(s).forEach( (elem, index) => {
if (pattern.test(elem)) {
result.push(index);
}
});
if (result.length == 0) {
return "заглавные буквы отсутствуют";
} else {
return result;
}
}

21
labs/lab9/desc.json

@ -0,0 +1,21 @@
{
"number": 9,
"task": "Создайте функцию, которая принимает массив имен супергероев и возвращает массив только имен супергероев, начинающихся на «человек». Верните имена в алфавитном порядке.",
"vars": [
[
{
"name": "names",
"desc": "Имена супергероев, разделенных запятой",
"data": ""
}
],
[
{
"name": "names",
"desc": "Имена супергероев, разделенных запятой",
"data": "Баба Нюра, Супермен, Человек Паук, человек невидимка"
}
]
],
"complete": true
}

35
labs/lab9/main.js

@ -0,0 +1,35 @@
"use strict";
function main(formName) {
let result = document.getElementById("result");
let names = document.forms[formName].elements[0].value;
if (!(typeof names === "string")) {
result.textContent = "Ошибка: names не является строкой!";
return;
}
result.textContent = "Результат: " + getNewNames(names);
}
function getNewNames(names) {
let result = [];
names = names.split(",");
names.forEach( elem => {
if ( elem.trim().toLowerCase().startsWith("человек") ) {
result.push( elem.trim() );
}
});
result.forEach( (elem, index, array) =>
array[index] = elem.split(/\s+/).map(word => word[0].toUpperCase() + word.substring(1)).join(' ')
);
result.sort();
if (result.length == 0) {
return "подходящие имена отсутствуют";
} else {
return result.join(', ');
}
}

18
main.go

@ -2,6 +2,7 @@ package main
import (
"embed"
"flag"
"io/fs"
"log"
"net/http"
@ -21,9 +22,20 @@ func main() {
http.HandleFunc("/", app.MainPageHandler)
http.HandleFunc("/lab", app.LabPageHandler)
http.Handle("/static/", http.FileServer(http.FS(app.WebFS)))
http.Handle("/labs/", http.FileServer(http.FS(app.LabsFS)))
http.HandleFunc("/coursework", app.CourseworkPageHandler)
debug := flag.Bool("d", false, "Debug flag for using local FS instead of embed")
flag.Parse()
if *debug {
http.Handle("/static/", http.FileServer(http.Dir("./web")))
http.Handle("/labs/", http.StripPrefix("/labs", http.FileServer(http.Dir("./labs"))))
log.Println("Starting in debug mode...")
} else {
http.Handle("/static/", http.FileServer(http.FS(app.WebFS)))
http.Handle("/labs/", http.FileServer(http.FS(app.LabsFS)))
log.Println("Starting in normal mode...")
}
err := http.ListenAndServe(":80", nil)
log.Fatal(err)

2
models/lab.go

@ -1,7 +1,7 @@
package models
type Lab struct {
Number string
Number int
Task string
Vars [][]Var
ScriptPath string

25
web/static/styles.css

@ -67,6 +67,20 @@ a.blocked {
cursor: default;
}
p {
text-align: justify;
margin-bottom: .5%;
}
.fail {
text-align: center;
color: red;
}
.success {
text-align: center;
color: green;
}
hr {
margin: .5% 0;
border: none;
@ -100,3 +114,14 @@ input[type=button] {
input[type=button]:hover {
background-color: #D8DDDD;
}
table {
border-collapse: collapse;
margin: auto;
}
th, td {
border: 2px solid;
padding: 1%;
width: 40%;
}

26
web/templates/coursework.html

@ -0,0 +1,26 @@
<!doctype html>
<html lang="ru">
<head>
<meta charset="utf-8">
<title>Курсовая работа</title>
<link rel="icon" type="image/png" sizes="256x256" href="static/favicon.png">
<link rel="stylesheet" type="text/css" href="static/styles.css">
</head>
<body>
<div class="main">
<h1>Курсовая работа</h1>
<p>Лягушка хочет перепрыгнуть реку, но она не может сделать это одним прыжком. При этом, в реке имеется n камней. Лягушка может прыгать с ближайшего берега на камень 1 и с камня n на дальний берег. Она также может прыгать с камня на камень, вперед и назад. Однако на каждом камне написано число j, и она должна перепрыгнуть ровно на j камней назад или вперед. Найдите минимальное количество прыжков для перехода через реку (включая прыжки с первого камня и с последнего камня (или любого другого камня, если возможно) на дальний берег) или определите отсутствие шансов, если невозможно перепрыгнуть реку. Лягушка может также добраться до дальнего берега от камня, отличного от n, если на нем написано достаточно большое число. n >= 2.</p>
<hr>
<form>
<label for="input">Метки на камнях:</label>
<input type="text" id="input" name="input" placeholder="Введите целые числа разделенные пробелом" value="1 3 5 3 2 3 1 0">
<input type="button" id="calculate" value="Вычислить" onclick="main();">
</form>
<div id="result"></div>
</div>
<script src="labs/coursework.js"></script>
</body>
</html>

1
web/templates/index.html

@ -17,6 +17,7 @@
{{ $k }}
</a>
{{ end }}
<a href="coursework">КР</a>
</div>
</div>
</body>

2
web/templates/lab.html

@ -29,6 +29,6 @@
{{ end }}
</div>
<script src="{{ .ScriptPath }}"></script>
<script src="labs/lab{{ .Number }}/main.js"></script>
</body>
</html>

Loading…
Cancel
Save