How can I start with this problem and fix my code? - c

The question: write a program that gets a list of numbers ( lets say 4 numbers ) and an extra number and checks if the extra number equals to the multiplying of two numbers from the list. If yes return true else return false.
For example a number list is ( 2,4,8,16) an extra number is 32, the program checks if 32 is equal to two numbers of the numbers from the list, and return true, in this example it will, because 32 equals to, my solution is below but its not correct, any help appreciated
int i;
int b;
int listA[4] = {2, 4, 8, 10};
printf("Enter your Extra number value \n");
scanf("%d", &b);
for(i=0; i<4; i++){//?
if(listA[i] * listA[i+] == b){// i+1 ?
printf("True! \n");
}else{
printf("False \n");
}

All you need is to write two nested loops.
You could write a separate function.
I suppose that the original array (list) is not necessary ordered.
For example
#include <stdio.h>
int is_multiplied( const int a[], size_t n, int value )
{
int result = 0;
if ( !( n < 2 ) )
{
for ( size_t i = 0; !result && i < n - 1; i++ )
{
for ( size_t j = i + 1; !result && j < n; j++ )
{
result = a[i] * a[j] == value;
}
}
}
return result;
}
int main(void)
{
int a[] = { 2, 4 , 8 , 10 };
const size_t N = sizeof( a ) / sizeof( *a );
int value = 32;
printf( "%s\n", is_multiplied( a, N, value ) ? "true" : "false" );
return 0;
}
The program output is
true

Since your code doesn't even compile. Id imagine you didn't put a lot of time into this.
int main()
{
int i;
int b;
int listA[4] = {2, 4 , 8 , 10};
bool verified = false;
printf("Enter your Extra number value \n");
scanf("%d" ,&b);
for(i=0; i<4 ; i++ )
{
for(int j=0; j<4; j++ )
{
if(j==i)
{
break;
}
if(listA[i] * listA[j] == b)
{
printf("True! \n");
verified = true;
continue;
}
else
{
//printf("False \n");
}
}
}
if(!verified)
{
printf("False \n");
}
}

To start with approach these sort of problems in the easiest possible method. using nested for loop.
As mentioned in one of the comments add a nested for loop.
int i=0;
int j=0;
int b=0;
int listA[4] = {2, 4 , 8 , 10};
printf("Enter your Extra number value \n");
scanf("%d" ,&b);
for(i=0; i<4 ; i++){//?
for (j=i; j<4; j++) {
if(listA[i] * listA[j] == b)
{
printf("True! \n");
return 0;
}
}
}
printf("False \n");
return 0;
Further optimization:-
for(i=0; i<4 ; i++){
if ((i > b) || ((b % i) != 0))
continue;
k = b/i;
for (j=i; j<4; j++) {
if(listA[j] == k)
{
printf("True! \n");
return 0;
}
}
}

Related

How do I reverse a specific row of a multidimensional array in C?

I have a multidimensional array with 3 rows and 4 columns. The program should use reverseRow()function to reverse a specific row from an array. Like, let's say user's input is 2, then it should reverse second row and print it.
I have tried a swap method, but it didn't work. I also tried using pointers, but it didn't work as well. Can someone explain it for me? How do I reverse a specific row?
#include <stdlib.h>
int arr[3][4] = {
{1, 2, 3, 4},
{5, 6, 7, 8},
{9, 10, 11, 12}};
int n = sizeof(arr) / sizeof(arr[0]);
void reverseRow(int low, int high)
{
if (low < high)
{
int temp = arr[low][0];
arr[low][0] = arr[high][0];
arr[high][0] = temp;
reverseRow(low + 1, high - 1);
for (int i = 0; i < n; i++)
for (int j = 3; i > 0; j--)
printf("%d ", arr[i][j]);
}
}
void printMenu()
{
printf("\n");
printf("You can choose one of these services: \n");
printf("1. Get the elements of a specific row reversed \n");
printf("Please select one to try ");
int answer;
scanf("%d", &answer);
switch (answer)
{
case 1:
reverseRow(0, n - 1);
break;
case 2:
printf("Bye!\n");
break;
default:
printf("please select carefully! \n");
break;
}
}
int main()
{
printMenu();
return 0;
}
Best regards.
You're reversing the first column, not a user-selected row.
You're not passing the row number to the function.
The loop that prints the array is printing all the columns in reverse order, and it's using n as the number of rows, not columns. I've renamed the variables to be clearer and fixed the printing loop.
#include <stdio.h>
#include <stdlib.h>
int arr[3][4] = {
{1, 2, 3, 4},
{5, 6, 7, 8},
{9, 10, 11, 12}};
int rows = sizeof(arr) / sizeof(arr[0]);
int cols = sizeof(arr[0]) / sizeof(arr[0][0]);
void reverseRow(int rownum, int low, int high)
{
if (low < high)
{
int temp = arr[rownum][low];
arr[rownum][low] = arr[rownum][high];
arr[rownum][high] = temp;
reverseRow(rownum, low + 1, high - 1);
} else {
for (int i = 0; i < rows; i++) {
for (int j = 0; j < cols; j++) {
printf("%d ", arr[i][j]);
}
printf("\n");
}
}
}
void printMenu()
{
printf("\n");
printf("You can choose one of these services: \n");
printf("1. Get the elements of a specific row reversed \n");
printf("Please select one to try ");
int answer;
scanf("%d", &answer);
switch (answer)
{
case 1:
printf("Please select row number: ");
int row;
scanf("%d", &row);
if (row >= rows || row < 0) {
printf("Invalid row\n");
break;
}
reverseRow(row, 0, cols - 1);
break;
case 2:
printf("Bye!\n");
break;
default:
printf("please select carefully! \n");
break;
}
}
int main()
{
printMenu();
return 0;
}
What is the row of a two-dimensional array?
It is a one dimensional array.
So what you need is to write a function that reverses a one-dimensional array.
An iterative function can look the following way
void reverseRow( int *a, size_t n )
{
for ( size_t i = 0; i < n / 2; i++ )
{
int tmp = a[i];
a[i] = a[n-i-1];
a[n-i-1] = tmp;
}
}
A recursive function can look the following way
void reverseRow( int *a, size_t n )
{
if ( !( n < 2 ) )
{
int tmp = a[0];
a[0] = a[n-1];
a[n-1] = tmp;
reverseRow( a + 1, n - 2 );
}
}
And either function is called like for example
reverseRow( arr[1], 4 );
that reverses the second row of the original array.
Or if the number of row (starting from 0) is stored in some variable as for example row then the function is called like
reverseRow( arr[row], 4 );
To output the reversed row you need to write a separate function.
Here is a demonstration program.
#include <stdio.h>
void reverseRowIterative( int *a, size_t n )
{
for (size_t i = 0; i < n / 2; i++)
{
int tmp = a[i];
a[i] = a[n - i - 1];
a[n - i - 1] = tmp;
}
}
void reverseRowRecursive( int *a, size_t n )
{
if (!( n < 2 ))
{
int tmp = a[0];
a[0] = a[n - 1];
a[n - 1] = tmp;
reverseRowRecursive( a + 1, n - 2 );
}
}
void printRow( const int *a, size_t n )
{
for (size_t i = 0; i < n; i++)
{
printf( "%2d ", a[i] );
}
putchar( '\n' );
}
int main( void )
{
enum { M = 3, N = 4 };
int arr[M][N] =
{
{ 1, 2, 3, 4 },
{ 5, 6, 7, 8 },
{ 9, 10, 11, 12 }
};
for ( size_t i = 0; i < M; i++ )
{
reverseRowIterative( arr[i], N );
printRow( arr[i], N );
}
putchar( '\n' );
for (size_t i = 0; i < M; i++)
{
reverseRowRecursive( arr[i], N );
printRow( arr[i], N );
}
putchar( '\n' );
}
The program output is
4 3 2 1
8 7 6 5
12 11 10 9
1 2 3 4
5 6 7 8
9 10 11 12

Is book's code to find the second largest integer in an array wrong?

This program is supposed to find the second largest integer. I have taken it from a book.
When I enter to find the second largest number among 4 5 1 2 3, it doesn't pick 4 as the second largest. I think on line 16 the code should be arr[0] and not arr[1]. Am I correct or am I missing something?
#include <stdio.h>
int main()
{
int i, n, arr[20], large, second_large;
printf("\n Enter the number of elements in the array : ");
scanf("%d", &n);
printf("\n Enter the elements");
for(i=0;i<n;i++)
scanf("%d",&arr[i]);
large = arr[0];
for(i=1;i<n;i++)
{
if(arr[i]>large)
large = arr[i];
}
second_large = arr[1]; // line 16
for(i=0;i<n;i++)
{
if(arr[i] != large)
{
if(arr[i]>second_large)
second_large = arr[i];
}
}
printf("\n The numbers you entered are : ");
for(i=0;i<n;i++)
printf("\t %d", arr[i]);
printf("\n The largest of these numbers is : %d",large);
printf("\n The second largest of these numbers is : %d",second_large);
return 0;
}
Your code reads like "C", this is C++20 code for the same problem :
(for manual input, use std::cin and values.push_back)
#include <vector>
#include <iostream>
#include <algorithm>
int main()
{
constexpr std::size_t second_largest_index = 1ul;
std::vector<int> values{ 0,2,8,7,5,4,1,3,9,6 };
std::ranges::nth_element(values, values.begin() + 1, std::ranges::greater());
std::cout << "the second largest value = " << values[second_largest_index];
return 0;
}
This statement
second_large = arr[1];
at once selects the largest number in the array { 4, 5, 1, 2, 3 }.
So the expression of the nested if statement within this for loop
for(i=0;i<n;i++)
{
if(arr[i] != large)
{
if(arr[i]>second_large)
second_large = arr[i];
}
}
never evaluates to true. That is the second largest number will always equal to the first largest number.
Pay attention to that in general an array can contain all elements equal each other.
I can suggest the following approach.
large = 0;
second_large = n;
i = 1;
while ( i < n && arr[i] == arr[large] ) ++i;
if ( i < n )
{
if ( arr[large] < arr[i] )
{
large = i;
second_large = 0;
}
else
{
second_large = i;
}
while ( ++i < n )
{
if ( arr[large] < arr[i] )
{
second_large = large;
large = i;
}
else if ( arr[second_large] < arr[i] )
{
second_large = i;
}
}
}
if ( second_large == n )
{
puts( "\nAll elements are equal each other." );
}
else
{
printf("\nThe largest of these numbers is : %d", arr[large] );
printf("\nThe second largest of these numbers is : %d", arr[second_large] );
}
Here is a demonstration C program (It is a C program because the program provided by you in fact has nothing from C++)
#include <stdio.h>
int main( void )
{
int arr[] = { 4, 5, 1, 2, 3 };
const size_t n = sizeof( arr ) / sizeof( *arr );
size_t large = 0;
size_t second_large = n;
size_t i = 1;
while (i < n && arr[i] == arr[large]) ++i;
if (i < n)
{
if (arr[large] < arr[i])
{
large = i;
second_large = 0;
}
else
{
second_large = i;
}
while (++i < n)
{
if (arr[large] < arr[i])
{
second_large = large;
large = i;
}
else if (arr[second_large] < arr[i])
{
second_large = i;
}
}
}
for (i = 0; i < n; i++)
{
printf( "%d ", arr[i] );
}
putchar( '\n' );
if (second_large == n)
{
puts( "All elements are equal each other." );
}
else
{
printf( "The largest of these numbers is : %d\n", arr[large] );
printf( "The second largest of these numbers is : %d\n", arr[second_large] );
}
}
The program output is
4 5 1 2 3
The largest of these numbers is : 5
The second largest of these numbers is : 4
A C++ demonstration program can look the following way
#include <iostream>
#include <functional>
#include <iterator>
#include <algorithm>
int main()
{
int arr[] = { 4, 5, 1, 2, 3 };
const size_t n = sizeof( arr ) / sizeof( *arr );
auto last = std::next( arr, n );
for (auto first = std::begin( arr ); first != last; ++first)
{
std::cout << *first << ' ';
}
std::cout << '\n';
auto it = std::adjacent_find( std::begin( arr ), last,
std::not_equal_to<>() );
if (it == last)
{
std::cout << "All elements are equal each other.\n";
}
else
{
auto [second_large, large] = std::minmax( { it, std::next( it ) },
[]( const auto &it1, const auto &it2 )
{
return *it1 < *it2;
} );
for (auto current = std::next( it, 2 ); current != last; ++current)
{
if (*large < *current)
{
second_large = std::exchange( large, current );
}
else if (*second_large < *current)
{
second_large = current;
}
}
std::cout << "The largest of these numbers is "
<< *large << " that is present at position "
<< std::distance( std::begin( arr ), large )
<< '\n';
std::cout << "The second largest of these numbers is "
<< *second_large << " that is present at position "
<< std::distance( std::begin( arr ), second_large )
<< '\n';
}
}
The program output is
4 5 1 2 3
The largest of these numbers is 5 that is present at position 1
The second largest of these numbers is 4 that is present at position 0
There are some minor errors in the code itself that can cause the problem.
Once, As you know that the array starts at index 0 but in the for loop you did count it from 1. so instead of:
for(i=1;i<n;i++)
{
if(arr[i]>large)
large = arr[i];
}
You should start your for loop also from zero, otherwise, you are not counting one.
Also for more simplicity, you can write your code like this:
#include <iostream>
using namespace std;
int main(){
int n, num[50], biggest, secondBiggest;
cout<<"Enter number of elements in your array: ";
cin>>n;
for(int i=0; i<n; i++){
cout<<"Enter your "<<(i+1)<<" Number: ";
cin>>num[i];
}
if(num[0]<num[1]){
biggest= num[1];
secondBiggest= num[0];
}
else{
biggest= num[0];
secondBiggest= num[1];
}
for (int i = 2; i< n ; i ++) {
if (num[i] > biggest) {
secondBiggest= biggest;
biggest= num[i];
}
else if (num[i] > secondBiggest && num[i] != biggest) {
secondBiggest= num[i];
}
}
cout<<"Second Largest Element in array is: "<<secondBiggest;
return 0;
}

Find the number that appears the most in an array

I have been debugging this problem for one night but still have no idea what has gone wrong. Let's say I input an array of 6 numbers which is {100,150,150,200,200,250} since 150 and 200 appear the same number of time then output the smaller number.
#include <stdio.h>
#include <stdlib.h>
int main() {
int arr[20] = { NULL }, num, result;
printf("Input a number(1-20) and enter a series of numbers in ascending order: \n");
scanf_s("%d", &num);
for (int k = 0; k < num; k++) {
scanf_s("%d", &arr[k]);
}
int c1, c2, i, j;
int temp = 0;
j = result = 0;
c1 = c2 = 1;
for (i = 1; i <= num-2; i++) { /*Add c1 if the value is the same*/
int a = arr[i];
if (arr[i+1] == a) c1++;
else {
j = i + 1;
temp = arr[j];
while (1) {
if (arr[j+1] == temp) {
c2++;
j++;
}
else break;
}
}
if (c2 > c1) { /*Move i to the position after j*/
c1 = 0;
result = temp;
}
if ((c2 < c1) || (c2 == c1)) { /*Move j to the next position*/
result = a;
c2 = 0;
}
i = j + 1;
}
printf("Number that appears the most time:%d\n", result);
return 0;
}
Will edit everytime after I did some progress
This is what I have done so far.
The output is correct for {100,150,150,200,200,250} but now the loop is stuck if I input a larger array with 8 numbers {100,100,100,150,150,200,250,300}. Help##
The error is in this part:
while (i <= num) { /*Add c1 if the value is the same*/
if (arr[i+1] == a)
Here i should be less than num-1, as you get numbers, the index goes from 0 to num-1, normally i<num would be ok, but you have done i+1 inside the loop so loop must only run from 0 to num-2.
Though, from your logic it should be arr[i] not arr[i+1]
And this part
int a = arr[i];
if (arr[i+1] == a) c1++;
Why would you assign a to value of arr[i] then again check with arr[i+1]? you only get c1 increasing with every duplicate value.
And this part at the end.
i=j+1
which is causing the infinite loop.
This would probably solve your problem although it is not a good solution:
#include <stdio.h>
#include <stdlib.h>
int main() {
int arr[20], num, result;
printf("Input a number(1-20) and enter a series of numbers in ascending order: \n");
scanf("%d", &num);
printf("Now enter the numbers");
for (int k = 0; k < num; k++) {
scanf("%d", &arr[k]);
}
int c1, c2, i, j;
int temp = 0;
j = 0;
result=arr[0];
c2 = 1;
for (i = 0; i < num; i++) { /*Add c1 if the value is the same*/
int a = arr[i];
c1=1;
for(j=i+1;j<num;j++)
{
if (arr[i]==arr[j])
{
c1+=1;
}
}
if(c1>c2)
{
c2=c1;
result=arr[i];
}
else if(c1==c2 && result>arr[i])
{
result=arr[i];
}
}
printf("Number that appears the most time:%d\n", result);
return 0;
}
Other than that, it has a better approach for your problem. make a struct of {int key, int count} then use it to store counts of all unique members in your array, then extract what you need.
Here is the code to what i was saying about, it might be hard to look into if you don't know about pointers & dynamic memory yet. but you'll get the logic.
#include<stdio.h>
#include<stdlib.h>
int main()
{
struct counts
{
int key;
int count;
};
int * data;
int num;
printf("Enter the number of data:");
scanf("%d",&num);
data=malloc(num*sizeof(int));
int i,j;
printf("Enter the data in order:");
for (i=0;i<num;i++)
{
scanf("%d",data+i);
}
struct counts *table;
int table_len=1;
int flag;
table=malloc(sizeof(struct counts));
table[0].key=data[0];
table[0].count=1;
for (i=1;i<num;i++)
{
flag=0;
for(j=0;j<table_len;j++)
{
if (table[j].key==data[i])
{
flag=1;
table[j].count+=1;
break;
}
}
if (flag==0)
{
table=realloc(table,++table_len* sizeof(struct counts));
table[table_len-1].key=data[i];
table[table_len-1].count=1;
}
}
//if you want to see at the table
printf("data\t\tcount\n");
for(i=0;i<table_len;i++)
{
printf(" %d\t\t%d\n",table[i].key,table[i].count);
}
//now to extract the value
int answer,count;
answer=table[0].key;
count=table[0].count;
for(i=1;i<table_len;i++)
{
if(count>table[i].count)
{
continue;
}
else if(count<table[i].count)
{
answer=table[i].key;
count=table[i].count;
}
else if(answer>table[i].key)
{
answer=table[i].key;
}
}
printf("The number with highest frequency is: %d\n",answer);
return 0;
}

Sorting an array meanwhile entering values

i need to sort the array while entering values that means that while the user enters numbers the array needs to sort itself: what i did so far is this:
void MoveRight(int *a,int n, int startIndex)
{
int j,temp;
j=n-1;
for(int i=startIndex;i<n;i++)
{
temp = a[j];
a[j]=a[i];
a[i]=temp;
}
}
void InsertionSort(int *a,int n)
{
int i,number,j;
printf("Enter %d numbers for the array\n",n);
for(i=0;i<n;i++)
{
scanf("%d",&number);
for(j=0;j<=i;j++)
{
if(number<a[j])
{
MoveRight(a,n,j);
a[j]=number;
break;
}
}
}
}
After entering: 1,3,2,4,5
The array i got was : -858993460,-858993460,-858993460,-858993460,-858993460
To apply the selection sort you should at first to enter all elements in the array.
These loops
for(i=0;i<n;i++)
{
scanf("%d",&number);
for(j=0;j<=i;j++)
{
if(number<a[j])
{
MoveRight(a,n,j);
a[j]=number;
break;
}
}
}
already result in undefined behavior because when i and j are equal to 0 then a[j] has indeterminate value. And moreover if the condition number<a[j] is not evaluated to true then nothing will be added to the array.
Function MoveRight does not make sense because in the loop variable j is not changed.
j=n-1;
for(int i=startIndex;i<n;i++)
{
temp = a[j];
a[j]=a[i];
a[i]=temp;
}
Here is a demonstrative program that shows how the task can be done.
#include <stdio.h>
void MoveRight( int *a, int n, int i )
{
for ( ; n != i; --n ) a[n] = a[n-1];
}
#define N 10
int main(void)
{
int a[N];
printf( "Enter %d numbers for the array: ", N );
for ( int i = 0; i < N; i++ )
{
int value;
scanf( "%d", &value );
int j = 0;
while ( j < i && !( value < a[j] ) ) j++;
MoveRight( a, i, j );
a[j] = value;
}
for ( int i = 0; i < N; i++ ) printf( "%d ", a[i] );
printf( "\n" );
return 0;
}
The program output might look the following way
Enter 10 numbers for the array: 5 2 3 9 8 1 6 7 4 0
0 1 2 3 4 5 6 7 8 9
Take into account that for large arrays it is much better to use the binary search instead of the sequential search to find the position where to insert the next value.

How to stop the value from becoming zero in every function call in the following code?

I am trying to write a code to solve the problem of taking two numbers m and n as an input from user and then calculating A(m,n) as follows:
1. A(m,n) = A(m,n-1) + A(m-1,n) , m,n >=0
2. A(m,n) = m-n if m<0 or n<0
I have written the following code in C, but the problem is that the answer coming is not correct, because the initialization of the variable value to zero, erases the value while recursion is going on and the answer I get is incorrect. Anybody knows how to solve this issue?
#include<stdio.h>
#include<stdlib.h>
int main()
{
int num1=0;
int num2=0;
int rows=0;
int columns=0;
int i,j,**array;
printf("Enter two non-negative integer numbers \n");
scanf("%d %d",&num1,&num2);
//create 2d-Array
rows=num1+1;
columns=num2+1;
array=malloc(rows * sizeof(int *));
for(i=0;i<rows;i++)
{
array[i]=malloc(columns*sizeof(int));
}
for (i = 0; i < rows; i++ )
{
for(j= 0; j < columns; j++ )
{
array[i][j]=0;
}
}
//Fill data in array
computeArray(array,rows,columns);
// Display contents of array
for (i = 0; i < rows; i++ )
{
for(j= 0; j < columns; j++ )
{
printf("array[%d][%d] = %d\n", i,j, array[i][j] );
}
}
getch();
return 0;
}
int computeArray (int **array, int rows, int columns)
{
int i,j;
for(i=0; i<rows;i++)
{
for(j=0;j<columns;j++)
{
array[i][j]=computeFunction(array,i,j);
}
}
return **array;
}
int computeFunction(int **array, int i, int j)
{
printf("Value reset by zero\n");
int value=0;
if((i<0)||(j <0))
{
value = i-j;
printf("Value contains i-j value\n");
return value;
}
else
{
value = (computeFunction(array,i,j-1)+ computeFunction(array,i-1,j));
printf("Value updated after else\n");
return value;
}
}
The answer for 0,0 should be -2, but I am getting 0 due to the initialization issue. Please let me know if you know how to overcome this issue?
It's being computed correctly - it should be 0.
A(m,n) = A(m,n-1) + A(m-1,n) , m,n >=0
A(m,n) = m-n if m<0 or n<0
So A(0,0) = A(0,-1) + A(-1,0) = (0 - (-1)) + (-1 - 0) = 1 + (-1) = 0

Resources