The seg fault issue is due to incorrect operation with strings and improper separation between local and global variables.
First, all char a[20] have to be changed to char a[21]. Same for char b[100][20] - it should be char b[100][21]. Per problem statement, the maximum size of the words is 20 characters. That means, however, that in order to store it and operate on it as a string object, we need to allocate 21 characters to reserve an extra space for null-terminated character.
As a follow-up, when making a copy of a string, you have to copy strlen(a)+1 characters in the strncpy call.
Second, when you accumulate the typed words, you keep the count in the global variable o but the accumulation happens in the local array b[100][20]. Therefore on every time call the b[100][20] array is brand new, and it is not in sync with the o counter.
Once all these issues are fixed, you also need to adjust the output since per problem statement an answer for each test case should be on a new line - you have to add \n to printf.
Here’s the adjusted code that gets AC:
#include <stdio.h>
#include <string.h>
int N,o=0,p;
char b[100][21]; // should be global otherwise modifications are
// inconsistent with 'o' counter changes
int time(char a[21])
{
int wt=2;
for(int i=1;i<strlen(a);i++)
{
if(a[i-1]==a[i])
wt=wt+4;
else if((a[i-1]=='d'&&a[i]=='f')||(a[i-1]=='f'&&a[i]=='d'))
wt=wt+4;
else if((a[i-1]=='j'&&a[i]=='k')||(a[i-1]=='k'&&a[i]=='j'))
wt=wt+4;
else
wt=wt+2;
}
for(int j=0;j<o;j++)
{
p=strncmp(b[j],a,strlen(a));
if((p==0) && (strlen(b[j]) == strlen(a)))
{
wt=wt/2;
break;
}
}
strncpy(b[o],a,strlen(a)+1); // +1 is for copying the null-terminating character
o++;
return wt;
}
int main()
{
int j,t=0,sum=0;
scanf("%d",&t);
for(int r=0;r<t;r++)
{
o = 0;
sum=0;
scanf("%d",&N);
char a[21];
for(int i=0;i<N;i++)
{
scanf("%s",&a);
sum=sum+time(a);
}
printf("%d\n",sum); // the end-of-line was missing in the output
}
return 0;
}
However I would solve the problem a bit differently. As you have seen, operating with strings on character level is quite error-prone. IMHO, it is easier and more robust to operate with strings directly, and also use some of the STL data structures like std::vector and std::set. Here’s how I see a better organized solution:
#include <bits/stdc++.h>
using namespace std;
int solve_word(const string& s) {
vector<int> hand;
for(int i=0; i<s.size(); ++i) {
hand.push_back((s[i]=='d' || s[i]=='f') ? 0 : 1);
}
int res = 2;
for(int i=1; i<s.size(); ++i) {
res += (hand[i-1] == hand[i]) ? 4 : 2;
}
return res;
}
int solve_test_case(const vector<string>& w) {
const int N = w.size();
set<string> typed;
int res = 0;
for(int i=0; i<N; ++i) {
int v = solve_word(w[i]);
if (typed.count(w[i])) {
v /= 2;
}
res += v;
typed.insert(w[i]);
}
return res;
}
int main() {
int T, N;
cin >> T;
for(int t=0; t<T; ++t) {
cin >> N;
vector<string> w(N);
for(int i=0; i<N; ++i) {
cin >> w[i];
}
int res = solve_test_case(w);
cout << res << endl;
}
return 0;
}
Thank you for solution.