Форум программистов, компьютерный форум, киберфорум
C# для начинающих
Войти
Регистрация
Восстановить пароль
 
Рейтинг 5.00/11: Рейтинг темы: голосов - 11, средняя оценка - 5.00
0 / 0 / 0
Регистрация: 01.10.2016
Сообщений: 54
1

TPL . Построить вектор, элементы которого равны произведению соответствующих элементов двух других векторов

14.10.2016, 23:27. Просмотров 1896. Ответов 9
Метки нет (Все метки)


Помогите написать код, используя библиотеку TPL (Task Parallel Library), класс Task.

Построить вектор, элементы которого равны произведению соответствующих элементов двух других векторов.

Как я понял необходимо перемножить 2 линейных массива.
0
Лучшие ответы (1)
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
14.10.2016, 23:27
Ответы с готовыми решениями:

Построить вектор, элементы которого равны произведению соответствующих элементов двух других векторов
Уважаемые участники форума, прошу вас помочь с созданием программы на C# со следующим условием: С...

Построить вектор, элементы которого равны произведению соответствующих элементов двух других векторов
Уважаемые участники форума, прошу вас помочь с созданием программы на C# со следующим условием: С...

Параллельное программирование:Построить вектор, элементы которого равны произведению соответствующих элементов
Уважаемые программисты,буду весьма признателен, если напишите код программы на C# к данной задаче:...

Сформировать вектор, каждый элемент которого равен произведению элементов соответствуюшей строки матрицы
Кто решит задачу тому 100 р на счет... Дан массив А (n,n), сформировать В(n), каждый элемент...

__________________
Помогаю в написании студенческих работ здесь.
Записывайтесь на профессиональные курсы С#-разработчиков‌
9
133 / 129 / 107
Регистрация: 17.03.2009
Сообщений: 364
15.10.2016, 05:23 2
Лучший ответ Сообщение было отмечено SancheZxZ как решение

Решение

Очень грубый код, сделанный наспех, но идею показывает.

Файл Program.cs

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
namespace MultVectors
{
    class Program
    {
        static int[] vector1 = new int[4] { 1, 2, 3, 4 };
        static int[] vector2 = new int[4] { 5, 6, 7, 8 };
        static int[] vector3 = new int[4];
 
 
        static void Main(string[] args)
        {
            var tasks = new List<Task>();
            for (var i = 0; i < vector1.Length; ++i)
            {
                tasks.Add(Task.Factory.StartNew((Object obj) =>
                    {
                        var j = (int)obj;
                        vector3[j] = vector1[j] * vector2[j];
                    }, 
                    i )
                );
            }
            
            Task.WaitAll(tasks.ToArray());
 
            for (var i = 0; i < vector1.Length; i++)
            {
                Console.WriteLine(vector1[i]+"*"+vector2[i]+"="+vector3[i]);
                
            }
            Console.ReadKey();
        }
    }
}
1
1412 / 1149 / 800
Регистрация: 29.02.2016
Сообщений: 3,513
15.10.2016, 10:38 3
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
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
using System;
using System.Text;
using System.Threading.Tasks;
using System.Threading;
using System.Diagnostics;
 
 
namespace ConsoleApplication
{
    class Program
    {
        static void Main(string[] args)
        {
            double[] array = new double[20 * 1000 * 1000];
            double[] brray = new double[20 * 1000 * 1000];
 
 
 
            for (int i = 0; i < array.Length; i++)
            {
                array[i] = 1;
                brray[i] = 1;
            }
 
                Stopwatch sw = Stopwatch.StartNew();
                CustomParallel(array, brray);
                Console.WriteLine("Custom parallel: {0:f2} s", sw.Elapsed.TotalSeconds);
 
                sw = Stopwatch.StartNew();
                CustomParallelExtractedMax(array, brray);
                Console.WriteLine("Custom parallel (extracted max): {0:f2} s", sw.Elapsed.TotalSeconds);
 
                sw = Stopwatch.StartNew();
                CustomParallelExtractedMaxHalfParallelism(array, brray);
                Console.WriteLine("Custom parallel (extracted max, half parallelism): {0:f2} s", sw.Elapsed.TotalSeconds);
 
 
                Console.ReadKey();
            }
 
  
 
        static void CustomParallel(double[] array, double[] brray)
        {
            var degreeOfParallelism = Environment.ProcessorCount;
 
            var tasks = new Task[degreeOfParallelism];
 
            for (int taskNumber = 0; taskNumber < degreeOfParallelism; taskNumber++)
            {
                int taskNumberCopy = taskNumber;
 
                tasks[taskNumber] = Task.Factory.StartNew(
                    () =>
                    {
                        for (int i = array.Length * taskNumberCopy / degreeOfParallelism;
                            i < array.Length * (taskNumberCopy + 1) / degreeOfParallelism;
                            i++)
                        {
                            array[i] = array[i] * brray[i];
                        }
                    });
            }
 
            Task.WaitAll(tasks);
        }
 
        static void CustomParallelExtractedMax(double[] array, double[] brray)
        {
            var degreeOfParallelism = Environment.ProcessorCount;
 
            var tasks = new Task[degreeOfParallelism];
 
            for (int taskNumber = 0; taskNumber < degreeOfParallelism; taskNumber++)
            {
                int taskNumberCopy = taskNumber;
 
                tasks[taskNumber] = Task.Factory.StartNew(
                    () =>
                    {
                        var max = array.Length * (taskNumberCopy + 1) / degreeOfParallelism;
                        for (int i = array.Length * taskNumberCopy / degreeOfParallelism;
                            i < max;
                            i++)
                        {
                            array[i] = array[i] * brray[i];
                        }
                    });
            }
 
            Task.WaitAll(tasks);
        }
 
        static void CustomParallelExtractedMaxHalfParallelism(double[] array, double[] brray)
        {
            var degreeOfParallelism = Environment.ProcessorCount / 2;
 
            var tasks = new Task[degreeOfParallelism];
 
            for (int taskNumber = 0; taskNumber < degreeOfParallelism; taskNumber++)
            {
                int taskNumberCopy = taskNumber;
 
                tasks[taskNumber] = Task.Factory.StartNew(
                    () =>
                    {
                        var max = array.Length * (taskNumberCopy + 1) / degreeOfParallelism;
                        for (int i = array.Length * taskNumberCopy / degreeOfParallelism;
                            i < max;
                            i++)
                        {
                            array[i] = array[i] * brray[i];
                        }
                    });
            }
 
            Task.WaitAll(tasks);
        }
    }
}
Добавлено через 23 минуты
добавил третий массив и сравнение с обычным умножением
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
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
using System;
using System.Text;
using System.Threading.Tasks;
using System.Threading;
using System.Diagnostics;
 
 
namespace ConsoleApplication
{
    class Program
    {
        static void Main(string[] args)
        {
            double[] array = new double[20 * 1000 * 1000];
            double[] brray = new double[20 * 1000 * 1000];
            double[] crray = new double[20 * 1000 * 1000];
 
 
 
            for (int i = 0; i < array.Length; i++)
            {
                array[i] = i;
                brray[i] = i;
            }
 
                Stopwatch sw = Stopwatch.StartNew();
                Serial(array, brray, crray);
                Console.WriteLine("Serial: {0:f2} s", sw.Elapsed.TotalSeconds);
 
                sw = Stopwatch.StartNew();
                CustomParallel(array, brray, crray);
                Console.WriteLine("Custom parallel: {0:f2} s", sw.Elapsed.TotalSeconds);
 
                sw = Stopwatch.StartNew();
                CustomParallelExtractedMax(array, brray, crray);
                Console.WriteLine("Custom parallel (extracted max): {0:f2} s", sw.Elapsed.TotalSeconds);
 
                sw = Stopwatch.StartNew();
                CustomParallelExtractedMaxHalfParallelism(array, brray, crray);
                Console.WriteLine("Custom parallel (extracted max, half parallelism): {0:f2} s", sw.Elapsed.TotalSeconds);
 
 
                Console.ReadKey();
            }
 
 
        static void Serial(double[] array, double[] brray, double[] crray)
        {
            for (int i = 0; i < array.Length; i++)
               crray[i] = array[i] * brray[i]; ;
        }
 
        static void CustomParallel(double[] array, double[] brray, double[] crray)
        {
            var degreeOfParallelism = Environment.ProcessorCount;
 
            var tasks = new Task[degreeOfParallelism];
 
            for (int taskNumber = 0; taskNumber < degreeOfParallelism; taskNumber++)
            {
                int taskNumberCopy = taskNumber;
 
                tasks[taskNumber] = Task.Factory.StartNew(
                    () =>
                    {
                        for (int i = array.Length * taskNumberCopy / degreeOfParallelism;
                            i < array.Length * (taskNumberCopy + 1) / degreeOfParallelism;
                            i++)
                        {
                            crray[i] = array[i] * brray[i];
                        }
                    });
            }
 
            Task.WaitAll(tasks);
        }
 
        static void CustomParallelExtractedMax(double[] array, double[] brray, double[] crray)
        {
            var degreeOfParallelism = Environment.ProcessorCount;
 
            var tasks = new Task[degreeOfParallelism];
 
            for (int taskNumber = 0; taskNumber < degreeOfParallelism; taskNumber++)
            {
                int taskNumberCopy = taskNumber;
 
                tasks[taskNumber] = Task.Factory.StartNew(
                    () =>
                    {
                        var max = array.Length * (taskNumberCopy + 1) / degreeOfParallelism;
                        for (int i = array.Length * taskNumberCopy / degreeOfParallelism;
                            i < max;
                            i++)
                        {
                            crray[i] = array[i] * brray[i];
                        }
                    });
            }
 
            Task.WaitAll(tasks);
        }
 
        static void CustomParallelExtractedMaxHalfParallelism(double[] array, double[] brray, double[] crray)
        {
            var degreeOfParallelism = Environment.ProcessorCount / 2;
 
            var tasks = new Task[degreeOfParallelism];
 
            for (int taskNumber = 0; taskNumber < degreeOfParallelism; taskNumber++)
            {
                int taskNumberCopy = taskNumber;
 
                tasks[taskNumber] = Task.Factory.StartNew(
                    () =>
                    {
                        var max = array.Length * (taskNumberCopy + 1) / degreeOfParallelism;
                        for (int i = array.Length * taskNumberCopy / degreeOfParallelism;
                            i < max;
                            i++)
                        {
                            crray[i] = array[i] * brray[i];
                        }
                    });
            }
 
            Task.WaitAll(tasks);
        }
    }
}
0
0 / 0 / 0
Регистрация: 01.10.2016
Сообщений: 54
15.10.2016, 10:40  [ТС] 4
afront, есть ли вариация более сокращенная? И если не сложно // сделайте коменты в коде...

Или же разбить элементы каждого массива допустим на 2 сектора и написать так, чтобы каждый поток выполнял
единовременное сложение каждого сектора. У нас 2 массива = 4 потока.
А след. потоком мы складываем элементы массивов.

Добавлено через 1 минуту
желательно попроще...
0
1412 / 1149 / 800
Регистрация: 29.02.2016
Сообщений: 3,513
15.10.2016, 10:45 5
сделайте коменты в коде
там и так все простыми словами написано

Или же разбить элементы каждого массива допустим на 2 сектора и написать так, чтобы каждый поток выполнял
попробуйте

желательно попроще
проще некуда
0
0 / 0 / 0
Регистрация: 01.10.2016
Сообщений: 54
15.10.2016, 10:50  [ТС] 6
afront, я студент. Так что не судите строго. Учусь только.
0
1412 / 1149 / 800
Регистрация: 29.02.2016
Сообщений: 3,513
15.10.2016, 11:03 7
SancheZxZ, и вы не судите строго вроде как помочь хотел
1
.NET senior
437 / 355 / 137
Регистрация: 23.09.2016
Сообщений: 980
15.10.2016, 14:02 8
SancheZxZ, написал свой вариант generic-класса для параллельной обработки векторов с возможностью партиционирования:

Кликните здесь для просмотра всего текста

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
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
using System;
using System.Threading.Tasks;
 
namespace CyberForum
{
    public class VectorWorker<TItem, TResult>
    {
        private TItem[] LeftVector;
        private TItem[] RightVector;
        private TResult[] ResultVector;
        private int[][] Partitions;
        Func<TItem, TItem, TResult> WorkerFunc;
        
        public VectorWorker(TItem[] leftVector, TItem[] rightVector, Func<TItem, TItem, TResult> workerFunc, int partitionsCount = 5)
        {
            // тут опционально можно прикрутить проверки на != null
            
            int resultLength = Math.Min(leftVector.Length, rightVector.Length);
            
            LeftVector = leftVector;
            RightVector = rightVector;
            ResultVector = new TResult[resultLength];
            
            WorkerFunc = workerFunc;
            
            Partitions = Partitionize(resultLength, partitionsCount);
        }
        
        public TResult[] ComputeResult()
        {
            int[][] partitions = Partitions;
            int partitionsCount = partitions.Length;
            
            Action<object> partitionFunction = ComputePartition;
            
            Task[] partitionTasks = new Task[partitionsCount];
            for (int idx = 0; idx < partitionsCount; ++idx)
            {
                partitionTasks[idx] = Task.Factory.StartNew(partitionFunction, partitions[idx]);
            }
            Task.WaitAll(partitionTasks);
            
            return ResultVector;
        }
        
        private void ComputePartition(object state)
        {
            int[] partitionIndices = state as int[];
            
            int startIndex = partitionIndices[0], endIndex = partitionIndices[1];
            
            Func<TItem, TItem, TResult> workerFunc = WorkerFunc;
            TItem[] leftVector = LeftVector;
            TItem[] rightVector = RightVector;
            TResult[] resultVector = ResultVector;
            
            for (int idx = startIndex; idx < endIndex; ++idx)
            {
                resultVector[idx] = workerFunc(leftVector[idx], rightVector[idx]);
            }
        }
        
        private int[][] Partitionize(int resultLength, int partitionsCount)
        {
            int delta = resultLength / partitionsCount;
            
            int[][] partitions = new int[partitionsCount][];
            
            for (int idx = 0; idx < (partitionsCount - 1); ++idx)
            {
                int startIndex = idx * delta;
                int endIndex = startIndex + delta;
                partitions[idx] = new[]{startIndex, endIndex};
            }
            
            partitions[partitionsCount - 1] = new[]{resultLength - delta, resultLength};
            
            return partitions;
        }
    }
}


Интерактивный пример кода с демонстрацией использования класса.

При необходимости / желании можно перевести его в full-generic формат, например так:
C#
1
public class VectorWorker<TLeft, TRight, TResult> { ... }
0
1412 / 1149 / 800
Регистрация: 29.02.2016
Сообщений: 3,513
15.10.2016, 14:22 9
bax_tang, ака SancheZxZ, и ни одного комментария, ужас
0
.NET senior
437 / 355 / 137
Регистрация: 23.09.2016
Сообщений: 980
15.10.2016, 15:10 10
Ну я стараюсь в коде нормальные имена использовать, поэтому должно быть понятно и один комментарий всё-таки есть!
1
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
15.10.2016, 15:10

Заказываю контрольные, курсовые, дипломные и любые другие студенческие работы здесь или здесь.

Сформировать массив, элементы которого равны произведению соответствующих элементов двух других массивов
Дано два массива одного размера. Сформулировать третий массив, элементы которого равны произведению...

Получить вектор, элементы которого равны суммам элементов соответствующих строк матрицы
Пожалуйста, помогите с решением. Дана матрица A(n на m) целых чисел. Получить вектор, элементы...

Получить вектор, элементы которого равны сумме минимального и максимального элементов соответствующих строк
Дана матрица A(n*n) целых чисел. Получить вектор, элементы которого равны сумме минимального и...

Построить вектор, элементы которого равны суммам элементов строк матрицы
Дана матрица: a11 ... a1n ... ... ... am1 ... amn Написать программу...


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

Или воспользуйтесь поиском по форуму:
10
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2021, vBulletin Solutions, Inc.