天天看點

筆試算法題(二)

題目描述

李雷和韓梅梅坐前後排。上課想說話怕老師發現,是以改為傳小紙條。為了被老師發現他們紙條上說的是啥,他們約定了如下方法傳遞資訊:

将26個英文字母(全為大寫),外加空格,一共27個字元分成三組,每組9個。也就是ABCDEFGHI是第一組,JKLMNOPQR是第二組,STUVWXYZ是第三組(此處用代表空格)。

然後根據傳遞紙條那天的日期,改變字母的位置

先根據月份數m, 以整個分組為機關進行循環左移,移動(m-1)次。然後根據日期數d,對每個分組内的字元進行循環左移,移動(d-1)次。

例如:以3月8号為例,首先移動分組,3月需要循環左移2次,變成:STUVWXYZ*,ABCDEFGHI,JKLMNOPQR

然後對每組内的字元,8日需要循環左移7次,最終程式設計:

Z*STUVWXY,HIABCDEFG,QRJKLMNOP

對于需要傳遞資訊中的每個字元。用組号群組内序号兩個數字來表示。

如果在3月8号需要傳遞資訊為“HAPPY”,那麼H位于第2組第1個,A位于第2組第3個…依次類推。是以最終紙條上寫成:

21 23 39 39 19

現給定日期和需要傳遞的資訊,請輸出應該寫在紙條上的編碼。

輸入規範

每個輸入包含兩行。第一行是用空格分隔的兩個數字,分别代表月份和日子。輸入保證是一個合法的日期

第二行為需要編碼的資訊字元串,僅由大寫字母A~Z和空格組成,字元串長度不超過1024個字元。

輸出規範

對每個輸入,列印對應的編碼,數字之間用空格分隔,每個輸出占一行。

輸入示例1:

3 8

HAPPY

輸出執行個體1:

21 23 39 39 19

輸入示例2:

2 14

I LOVE YOU

輸出執行個體2:

35 25 18 12 29 31 25 23 12 28

解題思路:

  1. 根據輸入的日期,将字元串循環變化出最終的三個字元串
  2. 根據傳遞字元串挨個字元進行查找(有點暴力…我認為這一步開始可以優化更好的方法)
  3. 先定位到組号,再定位到組内序号,直接輸出

代碼實作(C++):

#include <bits/stdc++.h>
#include <string>
using namespace std;
int main(){
	const string s[3] = {"ABCDEFGHI", "JKLMNOPQR", "STUVWXYZ*"};
	int n,m;
	cin>>n>>m;
	//第一步	要變換出最終的三個字元串 
	int year = (n-1)%3;
	int day = (m-1)%9;
	string s1[3];
	for(int i = 0; i < 3; i++){
		s1[i] = "";
		int count = year + i;
		if(count >= 3){
			count -= 3;
		}
		s1[i] = s[count].substr(day) + s[count].substr(0, day);
	}
	string str;
	cin.get();
	getline(cin, str);
	//第二步	根據傳遞資訊的字元串每個字元進行查詢輸出結果
	//第二步實作沒多想,很暴力,肯定有更優解
	for(int i = 0; i < str.length(); i++){
		for(int j = 0; j < 3; j++){			//定位組号 
			if((str[i] - s1[j][9-day] <= 8 && str[i] - s1[j][9-day] >= 0) || (s1[j][9-day] == 'S' && str[i] == ' ')){
				cout<<j+1;
				for(int k = 0; k < 9; k++){	//定位組内序号 
					if(str[i] == s1[j][k] || (str[i] == ' ' && s1[j][k] == '*')){
						cout<<k+1<<' ';
						break;
					}
				}
				break;
			}
		}
	}
	return 0;
}
           

以上就是一次真實的筆試題分享,希望有更好的思路或者不足之處歡迎在評論區指出,共同進步,謝謝

繼續閱讀