С Новым годом! Форум программистов, компьютерный форум, киберфорум
C# Windows Forms
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.50/8: Рейтинг темы: голосов - 8, средняя оценка - 4.50
10 / 10 / 3
Регистрация: 18.07.2010
Сообщений: 180

При загрузке картинки с большим количеством пикселей приложение закрывается

30.05.2012, 15:00. Показов 1857. Ответов 8
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Всем привет. Подскажите что я не так сделал. У меня в программе открывается картинка и создаётся булевый массив размером с картинку, потом рекурсивной функцией по пиксельно проверяется картинка и в массиве вместо фолс ставится тру(если пиксель проверен). Если картинка маленького разрешения то впринципи работает ещё более меняя, но вот при размере картинки от 500х500 программа отказывается работать.
Глобальные переменные:
C#
1
2
3
4
5
  bool [,]chk;
        Bitmap image1;
        Thread t;
        Thread u;
        int x=0, y=0;
Распечатка массива после обработки.
C#
1
2
3
4
5
6
7
8
9
10
 private void prnt()
        {
            for (int l = 0; l < image1.Width; l++)
            {
                for (int p = 0; p < image1.Height; p++)
                {
                    richTextBox1.Text += chk[l, p].ToString() + "\n";
                }
            }
        }
Функция открытия картинки и попиксельной проверки, также вызывается распечатка и рекурсивная функция
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
 private void button1_Click(object sender, EventArgs e)
        {
            if (openFileDialog1.ShowDialog() == DialogResult.OK)
            {
                System.IO.FileStream fs = new System.IO.FileStream(openFileDialog1.FileName, System.IO.FileMode.Open);
                image1 = new Bitmap(fs);
                fs.Close();
            }
            chk = new bool[image1.Width, image1.Height];
            for (int i = 0; i < image1.Width; i++)
            {
                for (int k = 0; k < image1.Height; k++)
                {
                    chk[i, k] = false;
                }
            }
            
            for (x = 0; x < image1.Width; x++)
            {
                for (y = 0; y < image1.Height; y++)
                {
                    Color pixelColor = image1.GetPixel(x, y);
                    Color newColor;
                    Color detected;
                  
                    detected = image1.GetPixel(x, y);
//проверка на пиксели
                    if ((detected.R >= 0 && detected.R <= 7) && (detected.G >= 0 && detected.G <= 7) && (detected.B >= 0 && detected.B <= 7))
                    {
                        newColor = Color.FromArgb(0, pixelColor.R, pixelColor.G, pixelColor.B);
                        image1.SetPixel(x, y, newColor);
                    }
                    else
                    {
                        newColor = Color.FromArgb(255, pixelColor.R, pixelColor.G, pixelColor.B);
                        image1.SetPixel(x, y, newColor);
                    }
                    if (chk[x, y] == false)
                    {
                        t = new Thread(delegate()
                           {
                               checkImage(x, y, image1, ref chk);  //рекурсивная функция
                           });
                        t.Start();
                    }
                    else
                    {
                        t.Abort();
                        continue;
                    }
                   // i++;
                }
            }
            u = new Thread(delegate()
                {
                    prnt();
                });
            u.Start();
            pictureBox1.Image = image1;
        }
Ну и сама рекурсивная функция
C#
1
2
3
4
5
6
7
8
9
10
11
12
 private void checkImage(int r,int e, Bitmap img,ref bool[,] ch)
        {
            if (e < 0 || r < 0 || r>=img.Width ||e>=img.Height)
                return;
            if (ch[r, e] == true)
                return;
            ch[r, e] = true;
            checkImage(r + 1, e, img, ref ch);
            checkImage(r, e+1, img, ref ch);
            checkImage(r - 1, e, img, ref ch);
            checkImage(r, e-1, img, ref ch);
        }
Также прилаживаю пример картинки.
Миниатюры
При загрузке картинки с большим количеством пикселей приложение закрывается  
0
IT_Exp
Эксперт
34794 / 4073 / 2104
Регистрация: 17.06.2006
Сообщений: 32,602
Блог
30.05.2012, 15:00
Ответы с готовыми решениями:

Будет ли тормозить приложение с большим количеством компонентов
На tabControle будет много разных панелей,ТексБоксов,Комбобоксов(на его страницах точнее). Страниц всего 3. Будет ли это сильно влиять...

Недостаточно памяти при работе с большим количеством изображений
Добрый вечер уважаемые форумчани. Помогите пожалуйста понять причину в коде. Сделал программу для ввода текста в изображение при массиве...

Сделать ProgressBar при зависании формы (работа с большим количеством данных)
Здравствуйте, нужно сделать progress bar на исполнение кода. Суть в том, что иде работа с большими файлами и форма зависает при выполнении...

8
10 / 10 / 3
Регистрация: 18.07.2010
Сообщений: 180
30.05.2012, 15:40  [ТС]
Ошибку частично отловил, но не пойму от куда она берётся
C#
1
2
3
4
5
6
7
8
9
10
11
12
  private void checkImage(int r,int e,Bitmap img,ref bool[,] ch)
        {
            if (e < 0 || r < 0 || r>img.Width ||e>img.Height)//выход за пределы массива,не пойму чего, пробовал создать массив на несколько символов больше всё равно не помогает.
                return;
            if (ch[r, e] == true)
                return;
            ch[r, e] = true;
            checkImage(r + 1, e,img, ref ch);
            checkImage(r, e+1,img, ref ch);
            checkImage(r - 1, e,img, ref ch);
            checkImage(r, e-1,img, ref ch);
        }
выскакивает только при загрузке картинки больше чем 100х100
0
 Аватар для DanielBecker
2 / 2 / 0
Регистрация: 26.05.2012
Сообщений: 12
30.05.2012, 17:41
Мне кажется программа просто жрет много ресурсов. У тебя там цикле поток создается и не один, плюс рекурсивная рекурсивная функция вызывается много раз из цикла и из самой себя. Посчитай какие участки когда сколько раз выполняются для разных по размеру изображений и выведи их на консоль.
0
10 / 10 / 3
Регистрация: 18.07.2010
Сообщений: 180
30.05.2012, 18:16  [ТС]
Допустим это изза рекурсии, так как даже если потоки не открываю, то таже беда.
Однако как это можно победить?
0
 Аватар для DanielBecker
2 / 2 / 0
Регистрация: 26.05.2012
Сообщений: 12
30.05.2012, 20:20
Насколько я понят программа ищет непрерывные области из пикселей удовлетворяющих данному условию. Это так?

Добавлено через 1 час 15 минут
Да вот это еще:

Цитата Сообщение от revaldo666 Посмотреть сообщение
C#
1
2
3
4
5
6
7
8
9
10
private void prnt()
  {
  for (int l = 0; l < image1.Width; l++)
    {
     for (int p = 0; p < image1.Height; p++)
       {
          richTextBox1.Text += chk[l, p].ToString() + "\n";
       }
     }
   }
Для картинки размером 500 на 500 это строчка
C#
1
* richTextBox1.Text += chk[l, p].ToString() + "\n";
250000 раз, плюс строка в нем может быть очень большой и из-за этого могут быть тормоза.
0
10 / 10 / 3
Регистрация: 18.07.2010
Сообщений: 180
30.05.2012, 23:19  [ТС]
рич текст едит не влияет на это
0
Футболист
 Аватар для Goal
533 / 435 / 142
Регистрация: 31.10.2011
Сообщений: 1,010
31.05.2012, 02:37
C#
1
2
3
4
5
6
7
8
9
10
11
12
private void checkImage(int r,int e, Bitmap img,ref bool[,] ch) throws Exception
        {
            if (e < 0 || r < 0 || r>=img.Width ||e>=img.Height)
                return;
            if (ch[r, e] == true)
                return;
            ch[r, e] = true;
            checkImage(r + 1, e, img, ref ch);
            checkImage(r, e+1, img, ref ch);
            checkImage(r - 1, e, img, ref ch);
            checkImage(r, e-1, img, ref ch);
        }
и узнаеш в чем проблема.
мб там ошибки)
0
1923 / 428 / 41
Регистрация: 12.07.2007
Сообщений: 2,062
31.05.2012, 07:20
revaldo666, в методе checkImage для больших картинок идет переполнение стека. Слишком глубокая рекурсия получается.
В добавок, идет перекрестный доступ к массиву в разных потоках, что ни к чему хорошему не приводит.
0
 Аватар для DanielBecker
2 / 2 / 0
Регистрация: 26.05.2012
Сообщений: 12
31.05.2012, 09:10
revaldo666, ищи алгоритм заливки области, тут посмотри:http://algolist.manual.ru/graphics/fill.php
Алгоритм рекурсивный, но рекурсия заменяется работой со стеком. А так у тебя из-за большой глубины рекурсии переполняется стек и программа падает.
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
BasicMan
Эксперт
29316 / 5623 / 2384
Регистрация: 17.02.2009
Сообщений: 30,364
Блог
31.05.2012, 09:10
Помогаю со студенческими работами здесь

Как выйти из цикла при проверки пикселей картинки?
Основной код: private void main() { string odnakr = null; try { ...

При открытии картинки фон сайта смещается вправо на 5 пикселей
Доброго времени суток. Встретился с странной проблемой. Когда открываешь картинку, фон сайта передвигается вправо на где то 5 пикселей......

IE открывается и закрывается сам. Потом гугл хром тупит при загрузке файлов
IE открывается и закрывается сам. Потом Сhrome тупит Установила Касперский какой-то, но без лицензии, ничего не нашел по вирусам в...

Закрывается приложение при strcpy
char g_aszEntName; strcpy( g_aszEntName, pszRight ); char pszRight - хранит строку в 21 символ. Добавлено через 5 минут А...

Не закрывается приложение при включенном StyleBook
Доброго, при включенном StyleBook, через некоторое время (во всех проектах) престают адекватно закрываться формы. То есть закрываю форму, а...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
9
Ответ Создать тему
Новые блоги и статьи
Модель микоризы: классовый агентный подход 3
anaschu 06.01.2026
aa0a7f55b50dd51c5ec569d2d10c54f6/ O1rJuneU_ls https:/ / vkvideo. ru/ video-115721503_456239114
Owen Logic: О недопустимости использования связки «аналоговый ПИД» + RegKZR
ФедосеевПавел 06.01.2026
Owen Logic: О недопустимости использования связки «аналоговый ПИД» + RegKZR ВВЕДЕНИЕ Введу сокращения: аналоговый ПИД — ПИД регулятор с управляющим выходом в виде числа в диапазоне от 0% до. . .
Модель микоризы: классовый агентный подход 2
anaschu 06.01.2026
репозиторий https:/ / github. com/ shumilovas/ fungi ветка по-частям. коммит Create переделка под биомассу. txt вход sc, но sm считается внутри мицелия. кстати, обьем тоже должен там считаться. . . .
Расчёт токов в цепи постоянного тока
igorrr37 05.01.2026
/ * Дана цепь постоянного тока с сопротивлениями и напряжениями. Надо найти токи в ветвях. Программа составляет систему уравнений по 1 и 2 законам Кирхгофа и решает её. Последовательность действий:. . .
Новый CodeBlocs. Версия 25.03
palva 04.01.2026
Оказывается, недавно вышла новая версия CodeBlocks за номером 25. 03. Когда-то давно я возился с только что вышедшей тогда версией 20. 03. С тех пор я давно снёс всё с компьютера и забыл. Теперь. . .
Модель микоризы: классовый агентный подход
anaschu 02.01.2026
Раньше это было два гриба и бактерия. Теперь три гриба, растение. И на уровне агентов добавится между грибами или бактериями взаимодействий. До того я пробовал подход через многомерные массивы,. . .
Советы по крайней бережливости. Внимание, это ОЧЕНЬ длинный пост.
Programma_Boinc 28.12.2025
Советы по крайней бережливости. Внимание, это ОЧЕНЬ длинный пост. Налог на собак: https:/ / **********/ gallery/ V06K53e Финансовый отчет в Excel: https:/ / **********/ gallery/ bKBkQFf Пост отсюда. . .
Кто-нибудь знает, где можно бесплатно получить настольный компьютер или ноутбук? США.
Programma_Boinc 26.12.2025
Нашел на реддите интересную статью под названием Anyone know where to get a free Desktop or Laptop? Ниже её машинный перевод. После долгих разбирательств я наконец-то вернула себе. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru