IPB
ЛогинПароль:

> Прочтите прежде чем задавать вопрос!

1. Заголовок темы должен быть информативным. В противном случае тема удаляется ...
2. Все тексты программ должны помещаться в теги [code=pas] ... [/code].
3. Прежде чем задавать вопрос, см. "FAQ", если там не нашли ответа, воспользуйтесь ПОИСКОМ, возможно такую задачу уже решали!
4. Не предлагайте свои решения на других языках, кроме Паскаля (исключение - только с согласия модератора).
5. НЕ используйте форум для личного общения, все что не относится к обсуждению темы - на PM!
6. Одна тема - один вопрос (задача)
7. Проверяйте программы перед тем, как разместить их на форуме!!!
8. Спрашивайте и отвечайте четко и по существу!!!

 
 Ответить  Открыть новую тему 
> Задача с двумерным массивом, Элементы равный сумме по...
Relrin
сообщение 1.12.2010 20:09
Сообщение #1


Пионер
**

Группа: Пользователи
Сообщений: 64
Пол: Мужской

Репутация: -  0  +


Дан массив A размерности n*m . Получить одномерный массив B, элементы которого получены путем суммирования элементов исходного массива , находящихся по периметрам.

В качестве примера, вот набросал, изображение такого рода:
Прикрепленное изображение

Прогресс не очень далеко, а может и нет. Работает правда этот кусочек кода для массива n*n, а вот для n*m ломаю голову... Пока дошел вот до этого:

k:=n div 2;
for i:=1 to k do begin
sum:=0;
{строки}
for j:=i to n-i+1 do
sum:=sum+x[i,j]+x[n-i+1,j];
{столбцы}
for j:=i+1 to n-i do
sum:=sum+x[j,i]+x[j,n-i+1];
writeln(sum); {вывод суммы}
end;
if n mod 2=1 then
writeln(x[k+1,k+1]);

 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
Relrin
сообщение 1.12.2010 20:34
Сообщение #2


Пионер
**

Группа: Пользователи
Сообщений: 64
Пол: Мужской

Репутация: -  0  +


Немного продвинулся вперед, однако, подсчитывает местами неправильно (скажем 3*3 считает правильно, если больше чем 3*3 - то уже неправильные подсчеты)
 
k:=n div 2;
p:=m div 2;
for i:=1 to k do
begin
for d:=1 to p do
begin
sum:=0;
{строки}
for j:=i to n-i+1 do
sum:=sum+a[i,j]+a[m-d+1,j];
{столбцы}
for j:=d+1 to m-i do
sum:=sum+a[j,i]+a[j,n-i+1];
b[count]:=sum;
if count<=i then count:=count+1;
end;
end;

if (n mod 2=1) and (m mod 2=1) and (n=m) then
b[count]:=a[k+1,p+1];



Сообщение отредактировано: Relrin - 1.12.2010 20:34
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
Krjuger
сообщение 1.12.2010 20:42
Сообщение #3


Профи
****

Группа: Пользователи
Сообщений: 652
Пол: Мужской
Реальное имя: Алексей

Репутация: -  20  +


Дам небольшую идею.Вот смотри,если матрица у нас не квадратная,и допустим n>m,то мы получим что строк больше столбцов (логично),но тогда у нас останется поледний центральный столбец,и несколько строк вместо одного центрального элемента,а если m>n,то ситуация получится обратной.Самое логичное разделить да 2 случая.Затем,поразмышляйте,как можно избавится от 2 внутрених циклов внутри for i:=1 to k do begin.Приглядитесь к ним,ведь они отличаются лиш чем?поменялись местами i,j и j вы учеличили на один)
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
Relrin
сообщение 1.12.2010 22:31
Сообщение #4


Пионер
**

Группа: Пользователи
Сообщений: 64
Пол: Мужской

Репутация: -  0  +


UP!
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
Lapp
сообщение 2.12.2010 7:12
Сообщение #5


Уникум
*******

Группа: Модераторы
Сообщений: 6 823
Пол: Мужской
Реальное имя: Лопáрь (Андрей)

Репутация: -  159  +


Боюсь, что все гораздо проще.. smile.gif
Способ, которым ты пошел, в корне порочен. Нет смысла обходить специальным образом, если все равно нужно просуммировать все. Основная идея - определить минимальное расстояние до края (расстояние до ближайшего края) массива. Это и будет "номер контура".
Вот тебе решение, разбирайся. Если будут вопросы - задавай, отвечу..

  if m<n then d:=(m-1)div 2+1 else d:=(n-1)div 2+1;  // calculating the b size
for i:=1 to m do for j:=1 to n do begin
k:=d; // set to max possible
if i<k then k:=i; // top distance
if j<k then k:=j; // left distance
if m-i+1<k then k:=m-i+1; // bottom distance
if n-j+1<k then k:=n-j+1; // right distance
Inc(b[k],a[i,j]); // adding to sum array
end;


--------------------
я - ветер, я северный холодный ветер
я час расставанья, я год возвращенья домой
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
Lapp
сообщение 2.12.2010 8:26
Сообщение #6


Уникум
*******

Группа: Модераторы
Сообщений: 6 823
Пол: Мужской
Реальное имя: Лопáрь (Андрей)

Репутация: -  159  +


Но если ты все же хочешь выяснить, как решить эту задачу обходом по отдельным периметрам (контурам), то вот тебе другое решение. Рекомендую тебе с ним тоже разобраться, поскольку лучше свои ошибки понимать до конца.

  if m<n then d:=(m-1)div 2+1 else d:=(n-1)div 2+1;  // calculate contours amount (size of b)
for i:=1 to d do begin // cycle through contours
for j:=i to m-i+1 do begin // rows (with edges)
Inc(b[i],a[j,i]);
if i<n-i+1 then Inc(b[i],a[j,n-i+1]); // do not count a central row twice
end;
for j:=i+1 to n-i do begin // columns (edges excluded)
Inc(b[i],a[i,j]);
if i<m-i+1 then Inc(b[i],a[m-i+1,j]); // do not count a central column twice
end
end;


--------------------
я - ветер, я северный холодный ветер
я час расставанья, я год возвращенья домой
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
Relrin
сообщение 2.12.2010 13:40
Сообщение #7


Пионер
**

Группа: Пользователи
Сообщений: 64
Пол: Мужской

Репутация: -  0  +


Цитата(Lapp @ 2.12.2010 9:26) *

Но если ты все же хочешь выяснить, как решить эту задачу обходом по отдельным периметрам (контурам), то вот тебе другое решение. Рекомендую тебе с ним тоже разобраться, поскольку лучше свои ошибки понимать до конца.
  if m<n then d:=(m-1)div 2+1 else d:=(n-1)div 2+1;  // calculate contours amount (size of b)
for i:=1 to d do begin // cycle through contours
for j:=i to m-i+1 do begin // rows (with edges)
Inc(b[i],a[j,i]);
if i<n-i+1 then Inc(b[i],a[j,n-i+1]); // do not count a central row twice
end;
for j:=i+1 to n-i do begin // columns (edges excluded)
Inc(b[i],a[i,j]);
if i<m-i+1 then Inc(b[i],a[m-i+1,j]); // do not count a central column twice
end
end;


Спасибо! Немного уже раскрутил задачу с твоей помощью. Только проблема с подсчетом неквадратной матрицы осталась, т.к. подсчеты неправильные идут уже с первого элемента

Сообщение отредактировано: Relrin - 2.12.2010 14:44
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
Relrin
сообщение 2.12.2010 15:48
Сообщение #8


Пионер
**

Группа: Пользователи
Сообщений: 64
Пол: Мужской

Репутация: -  0  +


Проблема в подсчете неквадратной матрицы в том(установлены проверками), что при n<m(пускай будет 3*4) считает 2ой элемент по вертикали, если n>m, то по горизонтали
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
Relrin
сообщение 2.12.2010 16:36
Сообщение #9


Пионер
**

Группа: Пользователи
Сообщений: 64
Пол: Мужской

Репутация: -  0  +


Сейчас пытаюсь приделать условия к циклам. Отдельно считаем периметр если m>n и m<n... Нужна помощь blink.gif

if m<n then d:=(n-1)div 2+1 else d:=(m-1)div 2+1;
for i:=1 to d do begin
sum:=0;
if count<=i then count:=count+1;
{строки}
for j:=i to m-i+1 do
begin
sum:=sum+a[j,i];
if (i<n-i+1) and (m<=n) then sum:=sum+a[j,n-i+1];
if (i<m-i+1) and (m>n) then sum:=sum+a[j,m-i+1];
end;
{столбцы}
for j:=i+1 to n-i do
begin
sum:=sum+a[i,j];
if (i<m-i+1) and (m<=n) then sum:=sum+a[m-i+1,j];
if (i<n-i+1) and (m>n) then sum:=sum+a[n-i+1,j];
end;
b[count]:=sum;
end;
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
Relrin
сообщение 2.12.2010 21:03
Сообщение #10


Пионер
**

Группа: Пользователи
Сообщений: 64
Пол: Мужской

Репутация: -  0  +


UP!!!
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
Lapp
сообщение 3.12.2010 0:10
Сообщение #11


Уникум
*******

Группа: Модераторы
Сообщений: 6 823
Пол: Мужской
Реальное имя: Лопáрь (Андрей)

Репутация: -  159  +


Цитата(Relrin @ 2.12.2010 13:40) *
Спасибо! Немного уже раскрутил задачу с твоей помощью. Только проблема с подсчетом неквадратной матрицы осталась, т.к. подсчеты неправильные идут уже с первого элемента
ЧТООО???... Эй, приятель.. Ты даешь себе отчет в том, что делаешь и пишешь?..
Я тебе дал ДВА ВЕРНЫХ РЕШЕНИЯ С ПОДРОБНЫМИ КОММЕНТАРИЯМИ. Они БЕЗУСЛОВНО работают со всеми матрицами любых соотношений длины и ширины. От тебя требовалось только переменные описать и ввести/вывести результат. Ты даже этого, не смог сделать, up'ник..

Хорошо, дополняю эти решения до целых программ.

Решение с обходом по контурам.
const
m=3;
n=4;
l=(m+n-1) div 4 +1;

var
a: array [1..m,1..n] of integer;
i,j,d: integer;
b: array [1..l] of integer;

begin
for i:=1 to m do begin
for j:=1 to n do begin
a[i,j]:=Random(10);
Write(a[i,j]:4)
end;
WriteLn
end;
WriteLn;
if m<n then d:=(m-1)div 2+1 else d:=(n-1)div 2+1; // calculate contours amount (size of b)
for i:=1 to d do begin // cycle through contours
for j:=i to m-i+1 do begin // rows
Inc(b[i],a[j,i]);
if i<n-i+1 then Inc(b[i],a[j,n-i+1]); // do not count last line twice
end;
for j:=i+1 to n-i do begin // columns
Inc(b[i],a[i,j]);
if i<m-i+1 then Inc(b[i],a[m-i+1,j]); // do not count last column twice
end
end;
for i:=1 to d do Write(b[i]:4);
ReadLn
end.


Решение со сквозным подсчетом (лучше).
const
m=4;
n=4;
l=(m+n-1)div 4+1;

var
a: array [1..m,1..n] of integer;
i,j,k,d: integer;
b: array [1..l] of integer;

begin
for i:=1 to m do begin
for j:=1 to n do begin
a[i,j]:=Random(10);
Write(a[i,j]:4)
end;
WriteLn
end;
WriteLn;
if m<n then d:=(m-1)div 2+1 else d:=(n-1)div 2+1; // calculating the b size
for i:=1 to m do for j:=1 to n do begin
k:=d; // set to max possible
if i<k then k:=i; // top distance
if j<k then k:=j; // left distance
if m-i+1<k then k:=m-i+1; // bottom distance
if n-j+1<k then k:=n-j+1; // right distance
Inc(b[k],a[i,j]); // adding to summ array
end;
for i:=1 to d do Write(b[i]:4);
ReadLn
end.


И кончай тут Up'ать каждый час. Тут не слепые собрались. Есть, что сказать - говори. А понукать будешь лошадей, когда сапоги выдадут..

-1 за нежелание вникать в ответы..


--------------------
я - ветер, я северный холодный ветер
я час расставанья, я год возвращенья домой
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 

 Ответить  Открыть новую тему 
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 



- Текстовая версия 18.07.2025 11:39
Хостинг предоставлен компанией "Веб Сервис Центр" при поддержке компании "ДокЛаб"