Домашние задания: Информатика

Функции и процедуры на Python

Тема по программированию "подпрограммы-функции". Надо написать программу на питоне с применением процедуры или функции. Задача: найти значения x=max(sqrt(D1),..,sqrt(Dn)),
y=max(sqrt(D1+x),..,sqrt(Dn+x)),
z=max(sqrt(D1+y),...,sqrt(Dn+y)),
где D - элемент вводимого массива, n - длина массива
у меня получилось решить это длинным способом без использования def
пожалуйста, помогите адаптировать алгоритм под условие задания

import math
s=input("Введите массив через пробел:")
o=s.split()
m=[int(t) for t in o]
n=len(m)
a=[]
b=[]
c=[]
for i in range (0,n):
a.append(math.sqrt(m[i]))
x=max(a)
for i in range (0,n):
b.append(math.sqrt(m[i]+x))
y=max(b)
for i in range(0,n):
c.append(math.sqrt(m[i]+y))
z=max(c)
print (a,b,c)
print('x=', round(x,2), 'y=', round(y,2), 'z=', round(z,2))
Для начала, функция квадратного корня монотонна на всей области определения (неотрицательных вещественных чисел). Поэтому максимумы второй и третьей операций будут стоять на тех же позициях, где максимум первой операции, и там же, где максимум исходного списка. Соответственно, остальные элементы промежуточных списков не нужны. В общем, и первый список тут не нужен, потому что нам требуется всего один проход. И позиция максимума нам не нужна, нужно только его значение. Можно обойтись генератором.
 from math import sqrt
m = (int(t) for t in input("Введите массив через пробел: ").split())
d = max(m)
x = sqrt(d)
y = sqrt(d + x)
z = sqrt(d + y)
print("x = %.2f y = %.2f z = %.2f" % (x, y, z))

Функции в языках программирования создаются для выделения логически завершённых фрагментов алгоритма, обладающих потенциалом повторного использования, или для которых требуется изоляция. Например, в опубликованном выше решении от нейросети трижды повторяющийся код по формированию промежуточных списков и поиска максимумов в них должен быть в отдельной функции, а то, как реализовано сейчас, - дилетантский подход.

В данном же алгоритме мы можем выделить функции в двух местах. Во-первых, можно отделить обработку от ввода и вывода данных:
 from math import sqrt
def maxsqrt(m):
d = max(m)
x = sqrt(d)
y = sqrt(d + x)
return (x, y, sqrt(d + y))

m = (int(t) for t in input("Введите массив через пробел: ").split())
print("x = %.2f y = %.2f z = %.2f" % maxsqrt(m))

Во-вторых, у нас есть однотипные вычисления корня, а это - уже повторение. Можно избавиться и от них:
 from itertools import accumulate as acc, chain as ch, repeat as rep
from math import sqrt

def sumsqrt(a, v): return sqrt(a + v)

def maxsqrt(m): return tuple(acc(ch((0,), rep(max(m), 3)), sumsqrt))[1:]

m = (int(t) for t in input("Введите массив через пробел: ").split())
print("x = %.2f y = %.2f z = %.2f" % maxsqrt(m))

В этой реализации мы формируем последовательность (0, d, d, d), где d = max(m), и свёртываем её, последовательно применяя sumsqrt и получая x, y, z в первом, втором и третьем элементах. Функция accumulate позволяет сохранить все промежуточные результаты свёртки. А нулевой элемент последовательности нам нужен только для начала вычислений, дальше его можно отбросить. Данный подход будет работать с произвольным количеством однотипных шагов по извлечению корня.
Vera Makarova
Vera Makarova
26 066
Лучший ответ
Для решения задачи необходимо написать функцию, которая будет принимать на вход массив D и его длину n, а затем находить значения x, y и z и возвращать их в виде кортежа.
Вот пример такой функции:
 import math 

def find_xyz(D, n):
a = [math.sqrt(D[i]) for i in range(n)]
x = max(a)
b = [math.sqrt(D[i]+x) for i in range(n)]
y = max(b)
c = [math.sqrt(D[i]+y) for i in range(n)]
z = max(c)
return (x, y, z)
Здесь мы определяем функцию find_xyz, которая принимает на вход массив D и его длину n. Затем мы создаем три списка a, b и c, в которых будут храниться значения, вычисленные на каждом из трех этапов. Для вычисления каждого списка мы используем цикл for и функцию math.sqrt для вычисления квадратного корня. Затем мы находим максимальные значения x, y и z с помощью функции max и возвращаем их в виде кортежа.
Чтобы использовать эту функцию, можно вызвать ее и передать ей массив D и его длину n, например:
 D = [1, 4, 9, 16, 25] 
n = len(D)
x, y, z = find_xyz(D, n)
print('x =', round(x, 2))
print('y =', round(y, 2))
print('z =', round(z, 2))
Здесь мы создаем массив D и находим его длину n. Затем мы вызываем функцию find_xyz и передаем ей массив D и его длину n. Результаты вычислений сохраняем в переменных x, y и z, которые затем выводим на экран с помощью функции print.
Например, для массива D = [1][2] функция find_xyz вернет кортеж (5.0, 7.0, 9.0), что означает, что x = 5.0, y = 7.0 и z = 9.0.
Владислав Кан Спасибо за подробное объяснение!)