Найти отрицательные значения в столбце

Задача: Задача 2. Даны матрицы В (m,n) и С (n,m). Определить, есть ли в заданных матрицах столбцы, содержащие по два отрицательных элемента. Вывести номера таких столбцов. Описать функцию для анализа одного столбца.

#include <stdio.h>
#include <stdlib.h>

void input(int nlines, int mcol, int a[]) {
    int i, j;
    for (i = 0; i < nlines; i++) {
        for (j = 0; j < mcol || (puts(""), 0); j++) {
            printf("a[%d][%d] = ", i, j);
            scanf("%d", &a[i * mcol + j]);
        }
    }
    printf("\n");
}

int check(int mcol, int nline, int a[]){
    int i,j;
   for (i = 0; i < mcol; i++) {
        int k = 0;
        for (j = 0; j < nline; j++) {
            if (a[i * nline + j] < 0) {
                k++;
            }
        }if(k==2){
        printf("stolb - %d\n",j);
        }else{
            printf("kol-vo < or >");
        }
    }
}


int main() {
    int n,m;
    printf("Введите значение, которое будет длиной матрицы B и шириной матрицы C: ");
    scanf("%d", &n);
    printf("Введите значение, которое будет шириной матрицы B и длиной матрицы C: ");
    scanf("%d", &m);
    int b[n][m], c[m][n];
    printf("Заполните первый массив: \n");
    input(n,m,&b[0][0]);
    printf("Заполните второй массив: \n");
    input(n,m,&c[0][0]);
    check(n,m,&b[0][0]);   
}

Проблема в том, что программа не считает первый столбец матрицы. Если размеры матриц будут 2х2 и ввести -1,1,-1,1 и еще раз так же, то будет вывод второго принта в функции check.


Ответы (3 шт):

Автор решения: MBo

Когда вы обходите матрицу как одномерный массив, индекс формируется как

index = строка * ширина + столбец

В этом цикле

 for (i=0; i<mcol; i++){
        int k=0;
        for(j=0; j<nline; i++){
            if(a[i*mcol+j]<0){
                k++;

очевидно, что i - столбец, а j - строка

→ Ссылка
Автор решения: Miracle-

Я понимаю, что так можно делать на C,хотя по сути это UB, но не лучше ли передать массив как двумерный? Можно сделать вот так, без двумерного массива:

for (i = 0; i < mcol; i++) {
        int k = 0;
        for (j = 0; j < nline; j++) {
            if (a[i * nline + j] < 0) {
                k++;
            }
        }
    }

Осталось придумать как подсчитывать индекс столбца.Надеюсь, что вам это поможет.

→ Ссылка
Автор решения: Harry

Я бы делал так:

#include <stdio.h>
#include <stdlib.h>

// Создание двумерной матрицы, ибо далеко
// не все компиляторы поддерживают VLA даже в C...
int ** makeMatrix(unsigned int n, unsigned int m)
{
    // Можно (и нужно) дописать проверки, что память выделена.
    // Для краткости не стал.
    int ** a = malloc(sizeof(int*)*n);
    for(unsigned int i = 0; i < n; ++i)
        a[i] = malloc(sizeof(int)*m);
    return a;
}

// Заполнение матрицы
void input(int ** A, unsigned int rows, unsigned int cols)
{
    for (unsigned int i = 0; i < rows; i++)
        for (unsigned int j = 0; j < cols; j++)
        {
            printf("a[%u][%u] = ", i, j);
            scanf("%d", &A[i][j]);
        }
}

// Подсчет количества отрицательных элементов в
// столбце colNo матрицы A
int minus_count(int ** A, unsigned int rows, unsigned int colNo)
{
    int cnt = 0;
    for(unsigned int i = 0; i < rows; ++i)
        cnt += (A[i][colNo] < 0);  // Для отрицательного дает 1
    return cnt;
}

// Проверка всех столбцов и вывод номеров тех, где ровно
// два отрицательных элемента
void check_2minus(int ** A, unsigned int rows, unsigned int cols)
{
    for(unsigned int i = 0; i < cols; ++i)
        if (minus_count(A,rows,i) == 2)
            printf("Столбец %d содержит два отрицательных элемента\n",i);
}

// Функция освобождения памяти
void freeMatrix(int ** A, unsigned int rows)
{
    for(unsigned int i = 0; i < rows; ++i) free(A[i]);
    free(A);
}

int main() {
    unsigned int n,m;
    printf("Введите количество строк матрицы B / столбцов матрицы C: ");
    scanf("%u", &n);
    printf("Введите количество столбцов матрицы B / строк матрицы C: ");
    scanf("%u", &m);

    int ** B = makeMatrix(n,m);
    int ** C = makeMatrix(m,n);

    printf("Заполните первый массив: \n");
    input(B, n, m);

    printf("Заполните второй массив: \n");
    input(C, m, n);

    puts("\n");  // "Просвет" перед выводом столбцов первой матрицы
    // Проверка первого массива
    check_2minus(B, n, m);

    puts("\n");  // "Просвет" перед выводом столбцов второй матрицы
    // Проверка второго массива
    check_2minus(C, m, n);

    // Освобождение памяти
    freeMatrix(B, n);
    freeMatrix(C, m);

}
→ Ссылка