首页 > 试题广场 >

ZOJ问题

[编程题]ZOJ问题
  • 热度指数:2358 时间限制:C/C++ 1秒,其他语言2秒 空间限制:C/C++ 64M,其他语言128M
  • 算法知识视频讲解
对给定的字符串(只包含'z','o','j'三种字符),判断他是否能AC。 是否AC的规则如下: 1. zoj能AC; 2. 若字符串形式为xzojx,则也能AC,其中x可以是N个'o' 或者为空; 3. 若azbjc 能AC,则azbojac也能AC,其中a,b,c为N个'o'或者为空;

输入描述:
输入包含多组测试用例,每行有一个只包含'z','o','j'三种字符的字符串,字符串长度小于等于1000。


输出描述:
对于给定的字符串,如果能AC则请输出字符串“Accepted”,否则请输出“Wrong Answer”。
示例1

输入

zoj
ozojo
ozoojoo
oozoojoooo
zooj
ozojo
oooozojo
zojoooo

输出

Accepted
Accepted
Accepted
Accepted
Accepted
Accepted
Wrong Answer
Wrong Answer
#include <iostream>
#
include <cstdio>
#include <string>

using namespace std;

int main(){
    
    string str;
    while(cin >> str){
        //只考虑了只有一个z和j的情况,以防万一可以再加一个判断,如果z或j多于一个则输出wrong。
        int pos1 = str.find('z');
        int pos2 = str.find('j');
        
        int a = pos1;
        int b = pos2 - pos1 -1;
        int c = str.size() - pos2 - 1;
        
        if( a*b==c && b>=1){
            printf("Accepted\n");
        }
        else{
            printf("Wrong Answer\n");
        }
        
    }
    return 0;
}
发表于 2020-02-27 11:13:54 回复(0)
/**
 * 思路:找到o的数量的关系即可
 *         'z'前面有a个'o';
 *         'z'与'j'之间有b个'o';
 *         'j'后面有c个'o';
 *         当满足b!==0 && c == a*b 的时候,就可以AC
 */


package n0713;

import java.util.Scanner;

import javax.sound.midi.MidiChannel;

public class ZOJ {

    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        
        while(in.hasNext()) {
            String input = in.nextLine();
            
            int beforNum=0;
            int minNum=0;
            int afterNum=0;
            
            int i=0;
            for(;i<input.length();i++) {
                char c = input.charAt(i);
                if(c =='z') {
                    break;
                }else {
                    beforNum++;
                }
            }
            
            for(i=i+1;i<input.length();i++) {
                char c = input.charAt(i);
                if(c=='j') {
                    break;
                }else {
                    minNum++;
                }
            }
            
            for(i=i+1;i<input.length();i++) {
                char c = input.charAt(i);
                if(c=='o') {
                    afterNum++;
                }else {
                    break;
                }
            }
//
//            System.out.println(beforNum);
//            System.out.println(minNum);
//            System.out.println(afterNum);
            if(minNum!=0   && afterNum == beforNum*minNum) {
                System.out.println("Accepted");
            }else {
                System.out.println("Wrong Answer");
            }
        }
    }
}

发表于 2019-07-13 23:55:10 回复(0)
#Python的简单实现,这里排版那么好看,就参考一下嘛:
#将ZOJ中的O转换成数字来查找是否满足条件
def findWhetherZOJ(leftNum,midNum,rightNum):
    if midNum==1:        #如果中间O的个数为1时左右O的个数必须相等(条件1和条件2)
        if leftNum==rightNum:
            return True
        else:
            return False
    elif midNum <= 0:    #如果中间O的个数为0则为输出错误
        return False
    else: #递归查找是否满足(条件3),条件3的结论和前提比较右边的O个数多一倍左边的个数,中间的O个数多一
        return findWhetherZOJ(leftNum,midNum-1,rightNum-leftNum)


while True:
    try:
        string = input()
        #剔除一些错误条件(Z和J必须为一个,剩余必须都为O,Z必须在J的前面)
        if string.count('z') != 1 or string.count('j') != 1 or string.count('o')+2 != len(string) or string.index('z')>string.index('j'):
            result = False
        else:
            leftNum = len(string[:string.index('z')])    #得到左边O的个数
            rightNum = len(string[string.index('j')+1:]) #得到右边O的个数
            midNum = len(string)-leftNum-rightNum-2      #得到中间O的个数
            result = findWhetherZOJ(leftNum,midNum,rightNum)
        if result:
            print('Accepted')
        else:
            print('Wrong Answer')
    except Exception:
        break

编辑于 2018-09-20 23:22:18 回复(0)

#include <iostream>

#include <cstring>

using namespace std;

bool ac(int oNum[3]){//判断是否能AC的函数
//oNum[0]是'z'前的'o'的个数,oNum[1]是'z' 'j'之间'o'的个数,oNum[2]是'j'后'o'个数
    if(oNum[1]<1)return false;// 中间至少有一个o

    if(oNum[0]<0||oNum[2]<0)return false;//小于0必然有问题

    if((oNum[0]==oNum[2])&&(oNum[1]==1)&&(oNum[0]>=0))return true;//情况1、2
    //递归判断情况3

    --oNum[1];

    oNum[2]-=oNum[0];

    return ac(oNum);

}

int main(int argc, char *argv[]) {

    char s[1005];

    while(scanf("%s",s)!=EOF){
//o[0]是'z'前的'o'的个数,o[1]是'z' 'j'之间'o'的个数,o[2]是'j'后'o'个数

        int o[3]={0};

        int index=0;

        for(int i=0;i<strlen(s);++i){//统计各个位置o的个数

            if(s[i]=='z'||s[i]=='j'){

                ++index;

                continue;

            }

            ++o[index];

        }

        if(ac(o))printf("Accepted\n");

        else printf("Wrong Answer\n");

    }

}

本题可以先统计 z  j 两个字符前、中间、后位置字符o的个数,然后判断各位置o的个数是否合法,情况1、2均比较好判断,情况3可以用递归判断转换成判断情况1、2。代码和解释见如上代码。
发表于 2018-05-19 14:35:33 回复(0)
#include <iostream>
#include <string>
using namespace std;
int main(){
    string s;
    while(cin>>s){
        int z=s.find("z");
        int j=s.find("j");
        if(z*(j-z-1)==s.size()-j-1&&j-z>1) cout<<"Accepted"<<endl;
        else cout<<"Wrong Answer"<<endl;
    }
    return 0;
}


编辑于 2020-03-03 11:48:09 回复(0)

解题思路:

    由题意可知下列几种情况:

        1 zoj

        2 x zoj x                                                              x ,y,a ,b,c为N个'o'或者为空;

        3 x  zyj  x*y

  (3) 由来:由于要使 a zbj c 能够 AC 过,根据( 2 )可知, a==c            

                                                                                     b = = 1 个'o'

 

a z b oj ac AC a z oo j 2*a AC

  有根据第三条条件,由于 a zooj 2*a AC ,即   a==c

                                                                          b== 2 个'o'

又可得 a z ooo j 3*a AC

由此类比得: a z b j a*b AC

综合( 1 ),( 2 )可知( 1 ,(2) 也符合表达式 a z b j a*b 。故只需要判断字符串是否符合 a z b j a*b 即可。

发表于 2017-05-20 15:45:37 回复(1)
首先字符串必须由z、o、j三种字符组成,有且只有一个z、有且只有一个j(且必须在z后方)、zj之间至少要有一个o,这些是前提条件,不满足的话就直接判错。
o有三种位置:z前、zj间、j后。(2)可以消掉z前和j后的o,(3)可以消掉zj间和j后的o。可以发现zj间的o只能通过(3)来消除。
那么,我们首先利用(3)来消除zj间的o(直到zj间只有一个o)。一次可以消掉一个zj间的o,并且j后的o要减少a个(不够的话就判错)。
当zj之间只剩一个o了,那就该利用(2)来消掉z前、j后的o了。显然,此时要是z前、j后o的数目相等,那就符合要求,否则就判错。
#include <stdio.h>
#include <string.h>
#define N 1001

int a, b, c;//abc分别表示z前、zj间、z后的'o'数量

bool Judge(char str[N])
{
    while(b>1)
    {
        b--;
        if(c>=a) c=c-a;
        else return false;
    }
    if(a==c) return true;
    else return false;
}

int main()
{
    char str[N];
    while(scanf("%s", str)!=EOF)
    {
        int len=strlen(str);
        int pz=-1, pj=-1;
        int nz=0, nj=0;
        a=0; b=0; c=0;
        bool ans=true;
        for(int i=0; i<len; i++)
        {
            if(str[i]=='z')
            {
                pz=i;
                nz++;
            }
            else if(str[i]=='j')
            {
                pj=i;
                nj++;
            }
            else if(str[i]=='o')
            {
                if(pz==-1&&pj==-1) a++;
                else if(pz!=-1&&pj==-1) b++;
                else if(pz!=-1&&pj!=-1) c++;
                else
                {
                    ans=false;
                    break;
                }
            }
            else
            {
                ans=false;
                break;
            }
        }
        if(ans==false || nz!=1 || nj!=1 || b<1)
        {
            printf("Wrong Answer\n");
            continue;
        }
        else
        {
            ans=Judge(str);
            if(ans==true) printf("Accepted\n");
            else printf("Wrong Answer\n");
        }
    }
    return 0;
}

编辑于 2018-03-08 17:11:28 回复(0)

从2可以得到,当中间有一个o,前后的o个数相等
由于3的 azbjc ,先假设b=1(一个o),则根据2有 a*1 = c
那么则有 azbojac 成立,即中间多一个‘o’, b=2 ,即a * 2 = ac (这里指o的个数),递推成立
又由于 a*1= c, 得出判定条件 c==a*b且b!=0 ,则可以AC 成立,且适用于三条规则
#include<iostream>
using namespace std;

int main()
{
    string str;
    while(cin>>str){

        int pos_z = str.find('z');  //测试用例没有两个z或j,所以这里不改了
        int pos_j = str.find('j');

        int a = pos_z; 
        int b = pos_j - pos_z - 1;
        int c = str.size() - pos_j - 1;

        if( pos_j - pos_z > 1 && c ==a*b)
            cout<<"Accepted"<<endl;
        else
            cout<<"Wrong Answer"<<endl;
    }
}


发表于 2020-04-01 11:54:58 回复(0)
#include<iostream>
#include<cstring>
using namespace std;
int main(void)
{
    string s;
    while(cin>>s){
        int z_index = s.find('z');
        int j_index = s.find('j');
        int front = z_index;
        int middle = j_index-z_index-1;
        int behind = s.length()-j_index-1;
        bool flag=false;
        while(middle>1)
        {
            behind-=front;
            middle--;
        }
        if(middle==1&&front==behind) flag=true;
        if(flag) cout<<"Accepted\n";
        else cout<<"Wrong Answer\n";
    }
    return 0;
}
编辑于 2019-05-09 00:11:40 回复(3)
#include <iostream>
#include <string>
using namespace std;

int main() {
    string str;
    while (cin >> str) {
        int pos_z = str.find('z');
        int pos_j = str.find('j');
        int a = pos_z;                      //'z'之前'o'的个数
        int b = pos_j - pos_z - 1;          //'z'和'j'之间'o'的个数
        int c = str.size() - pos_j - 1;     //'j'之后'o'的个数
        bool accept = true; //是否能AC
        if (b < 1) {
            accept = false;
            goto print;
        }
        while (b > 1 && c > a) {
            c -= a;
            b--;
        }
        if (b > 1 || c > a) {
            accept = false;
            goto print;
        }
        while (a > 0 && c > 0) {
            a--;
            c--;
        }
        if (a > 0 || c > 0) {
            accept = false;
        }
print:
        cout << (accept ? "Accepted" : "Wrong Answer") << endl;
    }
    return 0;
}

发表于 2024-03-03 15:11:07 回复(0)
#include "bits/stdc++.h"
using namespace std;
inline int read(){
    int x=0,f=1;
    char c=getchar();
    while (!(c<='9'&& c>='0')){
        if(c=='-')f=-1;
        c=getchar();
    }
    while (c<='9'&& c>='0'){
        x=(x<<3)+(x<<1)+(c^48);
        c=getchar();
    }
    return x*f;
}
string str;
bool Ac(string a) {
    if (a == "zoj")return 1;
    else {
        int posz = a.find('z');
        string zoj = "zoj";
        zoj.insert(0, posz, 'o');
        zoj.insert(zoj.size(), posz, 'o');
        if (zoj == a) return 1;
        else {
            int posj = a.find('j');
            int posc = posj + posz + 1;
            string zoj = "z";
            zoj.insert(0, posz, 'o');
            zoj.insert(zoj.size(), posj - posz - 2, 'o');
            zoj += "j";
            zoj.insert(zoj.size(), a.size() - posc, 'o');
            if (Ac(zoj)) return 1;
        }
    }
    return 0;
}

int main() {

    while (getline(cin,str)){
        try{
            if(Ac(str))cout<<"Accepted"<<endl;
        }catch(length_error) {
            cout<<"Wrong Answer"<<endl;
        }
    }
    return 0;
}

发表于 2023-08-16 15:27:57 回复(0)
这道题有点不讲武德,我写了一大段测试字符串是否符合azbjc的格式,最后发现,输入的字符串都符合这个格式,艹
#include <iostream>
using namespace std;

bool ac(int a,int b,int c){
    if(b==1&&a==c){
        return true;
    }else if(b==0){
        return false;
    }else{
        return ac(a,b-1,c-a);
    }
}

int main() {
    string s;
    while(cin>>s){
        int a=0,b=0,c=0,*p;
        p=&a;
        for(int i=0;i<s.size();i++){
            if(s[i]=='z'){
                p=&b;
            }else if(s[i]=='j'){
                p=&c;
            }else{
                (*p)++;
            }
        }
        
        if(ac(a,b,c)){
            printf("Accepted\n");
        }else{
            printf("Wrong Answer\n");
        }
    }
}


发表于 2023-02-20 20:43:07 回复(0)
#include<stdio.h>
#include<stdlib.h>
#include<math.h>
#include<string.h>
#include<malloc.h>
#include<limits.h>

int main()
{
    char str[1001];
    while(gets(str))
    {
        int len=strlen(str);
        int left=0,middle=0,right=0;
        int i=0;
        while(str[i]!='z'&&i<len)
        {
            left++;
            i++;
        }
        i++;
        while(str[i]!='j' &&i<len)
        {
            middle++;
            i++;
        }
        i++;
        while(i<len)
        {
            right++;
            i++;
        }
        
        //printf("%d %d %d\n",left,middle,right);
        if(right==middle*left && middle>0)
            printf("Accepted\n");
        else
            printf("Wrong Answer\n");
    }
}

发表于 2022-03-29 14:30:49 回复(0)
Accepted情况:
中间o数大于0;
同时满足以下任意一个:
    1.左边o数==右边o数(可同时为0);
    2.右边o数是左边o数的任意倍同时左边o数不为0.
#include <iostream>
#include <cstdio>
#include <cstring>

using namespace std;

int main() {
    string str;
    while (cin >> str) {
        int flag = 1;
        int a = 0, b = 0, c = 0;
        for (int i = 0; i < str.size(); ++i) {
            if (str[i] == 'z') {
                flag = 2;
            } else if (str[i] == 'j') {
                flag = 3;
            } else if (str[i] == 'o') {
                if (flag == 1) {
                    a++;
                } else if (flag == 2) {
                    b++;
                } else if (flag == 3) {
                    c++;
                }
            }
        }
        if (b >= 1) {
            if (a == c) {
                cout << "Accepted" << endl;
            } else if (a != 0 && c % a == 0) {
                cout << "Accepted" << endl;
            } else {
                cout << "Wrong Answer" << endl;
            }
        } else {
            cout << "Wrong Answer" << endl;
        }
    }
    return 0;
}


发表于 2021-03-16 16:05:07 回复(0)
看别人找的规律,我找不到
1.z和j有且仅有一组,且z要在前面
2.z前面的o的数量 x zj之间的o的数量 = j后o的数量
3.z和j之间至少要有一个o
#include<iostream>
#include<cstring> 
#include<cstdio>
using namespace std;
const int maxn = 1010;
// z 前面 'o' 的个数 ×z 和 j 中间 o 的个数 = j 后面 o 的个数
int main() {
	char str[maxn];
	while(cin >> str) {
		int cnt_oz = 0, cnt_zoj = 0, cnt_jo = 0;//	z前o,z和j之间的o,j后o的数量 
		int flag_z = 0, flag_j = 0;//判断是否有z和j
		bool flag = true; 
		for(int i = 0; i < strlen(str); ++i) {
//			先收到j或者z&nbs***bsp;j的数量大于1 
			if(flag_z < flag_j || flag_z > 1 || flag_j > 1) {
				flag = false;
				break;
			}
			if(str[i] == 'o') {
				if(flag_z == 0) cnt_oz++;
				else if(flag_j == 0) cnt_zoj++;
				else cnt_jo++;
			} 
			else if(str[i] == 'z') flag_z++;
			else if(str[i] == 'j') flag_j++;
		}
//		cout << cnt_oz << " " << cnt_zoj << " " << cnt_jo << endl;
		if(flag == false) {
			cout << "Wrong Answer" << endl;
			continue;
		} 
		if(cnt_oz * cnt_zoj == cnt_jo && cnt_zoj >= 1) {
			cout << "Accepted" << endl;
		} else {
			cout << "Wrong Answer" << endl;
		}
	}
	
	return 0;
}


发表于 2021-03-11 20:25:35 回复(0)
#include<iostream>
#include<string>
using namespace std;
bool isaccept(int a, int b, int c) {
    if (a == c && b == 1)return true;
    if (b < 1||c < a)return false;
    return isaccept(a, b - 1, c - a);
}
int main() {
    string str;
    while (cin >> str) {
        int a = str.find_first_of('z');
        int b = str.find_first_of('j') - a - 1;
        int c = str.size() - str.find_first_of('j') - 1;
        if (isaccept(a,b,c))cout << "Accepted"<<endl;
        else cout << "Wrong Answer" << endl;
    }
}
发表于 2021-03-11 14:51:52 回复(0)
//规律:z前面'o'的个数 × z和j中间o的个数=j后面o的个数
#include <iostream>
#include <string>
using namespace std;
int main(){
    string s;
    while(getline(cin,s)){
        int i = 0,len = s.size()-1;
        int num1 = 0,num2 = 0;
        while(s[i++] == 'o')
            num1++;
        while(s[len--] == 'o')
            num2++;
        int p = 0,q = 0,w = 0;
        for(int j = i - 1;j <= len+1;j++){
            if(s[j] == 'z')
                p++;
            else if(s[j] == 'o')
                q++;
            else
                w++;
        }
        if(p == 1 && w == 1 && q * num1 == num2){
            if((q == 0 && num1 != 0) || (q == 0 && num2 != 0))
                cout << "Wrong Answer" << endl;
            else
                cout << "Accepted" << endl;
        }else{
            cout << "Wrong Answer" << endl;
        }
    }
}

发表于 2021-03-10 16:34:23 回复(0)
#include<iostream>
#include<string>
using namespace std;

bool Judge(string s)
{
    int nz = 0,nj = 0,indexz,indexj;
    for(int i = 0;i < s.size();i++)
    {
        if(s[i] == 'z') nz++,indexz = i;
        if(s[i] == 'j') nj++,indexj = i;
    }
    if(nz != 1 || nj != 1 || indexj < indexz) return false;
    int n1 = 0,n2 = 0,n3 = 0;
    for(int i = 0;i < s.size();i++)
    {
        if(i < indexz && s[i] == 'o') n1++;
        else if(i < indexj && s[i] == 'o') n2++;
        else if(i > indexj && s[i] == 'o') n3++;
    }
    if(n1 == n3 && n2 == 1) return true;
    if(!n2) return false;
    n3 -= (n2 - 1) * n1;
    if(n1 != n3) return false;
    return true;
}

int main()
{
    string s;
    while(cin >> s)
    {
        if(Judge(s)) cout << "Accepted" << endl;
        else cout << "Wrong Answer" << endl;
    }
    return 0;
}

发表于 2021-02-21 18:14:40 回复(0)
双九十答案

#include <bits/stdc++.h>

using namespace std;

int main()
{
    string s;
    while(cin>>s){
        int num1=0, num2=0, num3=0;
        int zindex=0, jindex=0;
        for(int i=0; i<s.size(); i++){
            if(s[i]=='z') zindex = i;
            if(s[i]=='j'){
                jindex = i;
                break;
            }
        }
        num1 = zindex;
        num2 = jindex - zindex - 1;
        num3 = s.size() - jindex - 1;
        if(num1==0&&num3==0&&num2==1)
            cout<<"Accepted"<<endl;
        else if(num1==num3&&num2==1)
            cout<<"Accepted"<<endl;
        else if(num1!=0&&num3%num1==0&&num2>=2)
            cout<<"Accepted"<<endl;
        else
            cout<<"Wrong Answer"<<endl;
    }
    return 0;
}

发表于 2021-02-05 18:50:58 回复(0)
要么符合1,2,要么右边o个数-左边o个数并且中间o个数减1递归地符合1,2
#include <bits/stdc++.h>
using namespace std;
bool canAC(int lefto,int middleo,int righto)
{
    if(lefto<0||middleo==0)return false;
    if(lefto==righto)return true;
    return canAC(lefto,middleo-1,righto-lefto);
}
int main()
{
    string input;
    while(cin>>input)
    {
        int lefto,middlo,righto,posz=-1,posj=-2;
        for(int i=0;i<input.length()&&posz!=-100&&posj!=-100;++i)
        {
            if(input[i]=='z')posz=posz==-1&&posj==-2?i:-100;
            if(input[i]=='j')posj=posz!=-1&&posj==-2?i:-100;
        }
        lefto=posz,middlo=posj-posz-1,righto=input.length()-1-posj;
        printf("%s\n",canAC(lefto,middlo,righto)?"Accepted":"Wrong Answer");
    }
    return 0;
}


发表于 2020-04-15 20:31:59 回复(0)

问题信息

难度:
35条回答 4429浏览

热门推荐

通过挑战的用户

查看代码