Как указать суффикс для дней месяца?

Мне нужна функция для возврата суффикса в течение нескольких дней при отображении текста вроде «th» в «Wednesday June 5th, 2008».

Работать нужно только с числами от 1 до 31 (проверка ошибок не требуется) и на английском языке.


person paxdiablo    schedule 03.10.2008    source источник


Ответы (4)


Вот альтернатива, которая должна работать и для больших чисел:

static const char *daySuffixLookup[] = { "th","st","nd","rd","th",
                           "th","th","th","th","th" };

const char *daySuffix(int n)
{
    if(n % 100 >= 11 && n % 100 <= 13)
        return "th";

    return daySuffixLookup[n % 10];
}
person Adam Pierce    schedule 03.10.2008
comment
Это отличное решение - хотите использовать интернационализированную версию? - person belugabob; 17.04.2009
comment
P.S. Я знаю, что это не входило в исходный вопрос, но это интересное упражнение. - person belugabob; 17.04.2009
comment
Ха-ха, международная версия была бы совершенно другой, вероятно, поисковые таблицы были бы лучшим способом ее реализовать. - person Adam Pierce; 19.04.2009

Для C работает следующая функция:

char *makeDaySuffix (unsigned int day) {
    //if ((day < 1) || (day > 31)) return "";
    switch (day) {
        case 1: case 21: case 31: return "st";
        case 2: case 22:          return "nd";
        case 3: case 23:          return "rd";
    }
    return "th";
}

По запросу, это работает только для номеров от 1 до 31 включительно. Если вам нужна (возможно, но не обязательно) чистая скорость, вы можете попробовать:

char *makeDaySuffix (unsigned int day) {
    static const char * const suffix[] = {
        "st","nd","rd","th","th","th","th","th","th","th",
        "th","th","th","th","th","th","th","th","th","th"
        "st","nd","rd","th","th","th","th","th","th","th"
        "st"
    };
    //if ((day < 1) || (day > 31)) return "";
    return suffix[day-1];
}

Вы заметите, что у меня есть ограничения там, хотя я закомментировал. Если есть хотя бы малейшая вероятность того, что будет передано неожиданное значение, вы, вероятно, захотите раскомментировать эти строки.

Просто имейте в виду, что с современными компиляторами наивные предположения о том, что быстрее на языке высокого уровня, могут быть неверными: измеряйте, а не угадайте.

person paxdiablo    schedule 03.10.2008

const char *getDaySuffix(int day) {
    if (day%100 > 10 && day%100 < 14)
        return "th";
    switch (day%10) {
        case 1:  return "st";
        case 2:  return "nd";
        case 3:  return "rd";
        default: return "th";
    };
}

Этот работает для любого числа, а не только для 1-31.

person Milan Babuškov    schedule 03.10.2008
comment
Первая проверка также может быть if ((day % 100) / 10 == 1) return "th";. - person paxdiablo; 26.02.2016

См. Мой вопрос здесь: Как преобразовать кардинальные числа в порядковые (это не C #).

Резюме: похоже, что пока нет возможности, с вашими ограниченными требованиями вы можете просто использовать простую функцию, подобную той, что была опубликована.

person Roel    schedule 03.10.2008