拼字游戏 (word crosses)
问题描述:拼字游戏历史悠久,能锻炼人的思维和提高单词记忆量。在欧美报纸的版面中
经常会见到。本题只是简单地演示单组交叉词。所谓单组交叉词,是指两个单词交叉放置
,一个水平放置,另一个垂直放置,交叉点是两个单词都共用一个字母,而且交叉点遵循
交叉靠前原则,即这公用的字母尽量在水平单词的前方,然后也尽量在垂直单词的上方。
例如:DEFER ,PREFECT(前一个为水平单词)的交叉点是E ,而PREFECT
,EDFER 的交
叉点是R
。双交叉词是指有两组单组交叉词,它们的水平单词放在同一行。试编程将输入
的每四个一组的单词尽可能组成双交叉词。
n
输入:输入文件由若干行组成,每行有四个单词,按顺序每两个为一组,每组第一个单
词为水平单词,每个单词由1 到10
个大写字母组成,单词之间用一个空格隔开。最后一
行由一个"#"结束。
n
输出:输出文件由一系列双交叉词组成,每个水平单词之间隔三个空格。若不能构成双
交叉词,则显示"Unable to make two crosses"。每组双交叉词间空一行。
#include <stdio.h>
#include <string.h>
#define MAX_WORD_LENGTH 10
// 查找两个单词的交叉点,返回第一个单词中的交叉点位置(即第二个单词的所在位置)
int find_intersection(char word1[], char word2[], int length1, int length2){
// 遍历第一个单词的所有字母
for(int i=0; i<length1; i++){
// 遍历第二个单词的所有字母
for(int j=0; j<length2; j++){
// 如果发现了交叉点(即两个字母相同),则返回第一个单词中的交叉点位置
if(word1[i] == word2[j]){
return i;
}
}
}
// 如果没有找到交叉点,则返回-1
return -1;
}
// 打印水平单词,多余部分补上空格
void print_horizontal_word(char word[], int length){
printf("%s", word);
for(int i=length; i<MAX_WORD_LENGTH; i++){
printf(" ");
}
printf(" ");
}
// 打印垂直单词,多余部分补上空格,在交叉点前打印两个空格
void print_vertical_word(char word[], int length, int intersection_index){
// 先打印交叉点前的部分
for(int i=0; i<intersection_index; i++){
printf(" ");
printf("%c", word[i]);
printf("\n");
}
// 再打印交叉点以及交叉点后的部分
printf(" "); // 两个空格是为了和水平单词对齐
printf("%c", word[intersection_index]);
printf("\n");
for(int i=intersection_index+1; i<length; i++){
printf(" ");
printf("%c", word[i]);
printf("\n");
}
}
int main(){
char word1[MAX_WORD_LENGTH], word2[MAX_WORD_LENGTH], word3[MAX_WORD_LENGTH], word4[MAX_WORD_LENGTH];
int intersection_index1, intersection_index2;
while(1){
// 读取每行四个单词,按顺序每两个为一组,第一个单词为水平单词
scanf("%s %s %s %s\n", word1, word2, word3, word4);
if(word1[0] == '#'){
break;
}
// 找到两组单组交叉词之间的交叉点
int length1 = strlen(word1), length2 = strlen(word2);
intersection_index1 = find_intersection(word1, word2, length1, length2);
if(intersection_index1 == -1){
printf("Unable to make two crosses\n\n");
continue;
}
int length3 = strlen(word3), length4 = strlen(word4);
intersection_index2 = find_intersection(word3, word4, length3, length4);
if(intersection_index2 == -1){
printf("Unable to make two crosses\n\n");
continue;
}
// 打印双交叉词
printf(" ");
print_horizontal_word(word1, length1);
print_horizontal_word(word3, length3);
printf("\n");
for(int i=0; i<intersection_index1; i++){
printf(" ");
printf(" ");
printf("\n");
}
printf(" ");
printf("%c", word1[intersection_index1]);
printf(" ");
print_vertical_word(word4, length4, intersection_index2);
for(int i=intersection_index1+1; i<length1; i++){
printf(" ");
printf(" ");
printf("\n");
}
printf(" ");
print_horizontal_word(word2, length2);
print_horizontal_word(word4, length4);
printf("\n\n");
}
return 0;
}