Re: Тест по C++ для моих студентов
От: velkin Земля kisa.biz
Дата: 13.03.15 16:25
Оценка: +4
Здравствуйте, Tilir, Вы писали:

T>В свободное от работы время продолжаю учить детей добру и C++ (с упором на второе).

T>И вот вчера группа неплохо написала мне простенький midterm тестик на десять вопросов в части которых есть варианты ответа, в части — надо написать пару строчек несложного кода. Условия обычные -- 40 минут и никуда не подглядывать. Но что меня больше всего поразило -- какой фурор этот тест вызвал среди моих коллег, среди которых нашлось даже больше желающих попробовать в нем свои силы, чем среди студентов
T>Так что решил выложить сюда. Приветствуется конструктивная критика и все такое.

#include <cassert>  
template <typename T, typename U> bool 
operator == (const T &x, const U &y) 
{ 
  return !(x < y) && !(y < x);  
} 
template <typename T, typename U> bool 
operator != (const T &x, const U &y) 
{ 
  return !(x == y);  
} 
struct Pair  
{ 
  int m_x, m_y; 
  Pair (int x, int y = 0): m_x(x), m_y(y) {}  
};  
bool 
operator < (const Pair &lhs, const Pair &rhs) 
{ 
  return (lhs.m_x < rhs.m_x) || ((lhs.m_x == rhs.m_x) && (lhs.m_y < rhs.m_y)); 
}  
int 
main (void) 
{ 
  Pair a (2);  
  Pair b (2, 1);  
  int c = 2, d = 2; 
  /* 1 */ assert (b != a);  
  /* 2 */ assert (c == d); 
  /* 3 */ assert (a == c); 
  /* 4 */ assert (d == b); 
  return 0; 
}


gcc main.cpp

a.out

a.out: main.cpp:31: int main(): Assertion `d == b' failed.
Аварийный останов (сделан дамп памяти)


Ещё вопросы?

gcc --help

Usage: gcc [options] file...
Options:
...
  -S                       Compile only; do not assemble or link
..


gcc -S main.cpp

    .file    "main.cpp"
    .section    .text._ZN4PairC2Eii,"axG",@progbits,_ZN4PairC5Eii,comdat
    .align 2
    .weak    _ZN4PairC2Eii
    .type    _ZN4PairC2Eii, @function
_ZN4PairC2Eii:
.LFB3:
    .cfi_startproc
    pushl    %ebp
    .cfi_def_cfa_offset 8
    .cfi_offset 5, -8
    movl    %esp, %ebp
    .cfi_def_cfa_register 5
    movl    8(%ebp), %eax
    movl    12(%ebp), %edx
    movl    %edx, (%eax)
    movl    8(%ebp), %eax
    movl    16(%ebp), %edx
    movl    %edx, 4(%eax)
    popl    %ebp
    .cfi_restore 5
    .cfi_def_cfa 4, 4
    ret
    .cfi_endproc
.LFE3:
    .size    _ZN4PairC2Eii, .-_ZN4PairC2Eii
    .weak    _ZN4PairC1Eii
    .set    _ZN4PairC1Eii,_ZN4PairC2Eii
    .text
    .globl    _ZltRK4PairS1_
    .type    _ZltRK4PairS1_, @function
_ZltRK4PairS1_:
.LFB5:
    .cfi_startproc
    pushl    %ebp
    .cfi_def_cfa_offset 8
    .cfi_offset 5, -8
    movl    %esp, %ebp
    .cfi_def_cfa_register 5
    movl    8(%ebp), %eax
    movl    (%eax), %edx
    movl    12(%ebp), %eax
    movl    (%eax), %eax
    cmpl    %eax, %edx
    jl    .L3
    movl    8(%ebp), %eax
    movl    (%eax), %edx
    movl    12(%ebp), %eax
    movl    (%eax), %eax
    cmpl    %eax, %edx
    jne    .L4
    movl    8(%ebp), %eax
    movl    4(%eax), %edx
    movl    12(%ebp), %eax
    movl    4(%eax), %eax
    cmpl    %eax, %edx
    jge    .L4
.L3:
    movl    $1, %eax
    jmp    .L5
.L4:
    movl    $0, %eax
.L5:
    popl    %ebp
    .cfi_restore 5
    .cfi_def_cfa 4, 4
    ret
    .cfi_endproc
.LFE5:
    .size    _ZltRK4PairS1_, .-_ZltRK4PairS1_
    .section    .rodata
.LC0:
    .string    "main.cpp"
.LC1:
    .string    "b != a"
.LC2:
    .string    "c == d"
.LC3:
    .string    "a == c"
.LC4:
    .string    "d == b"
    .text
    .globl    main
    .type    main, @function
main:
.LFB6:
    .cfi_startproc
    pushl    %ebp
    .cfi_def_cfa_offset 8
    .cfi_offset 5, -8
    movl    %esp, %ebp
    .cfi_def_cfa_register 5
    andl    $-16, %esp
    subl    $48, %esp
    movl    $0, 8(%esp)
    movl    $2, 4(%esp)
    leal    32(%esp), %eax
    movl    %eax, (%esp)
    call    _ZN4PairC1Eii
    movl    $1, 8(%esp)
    movl    $2, 4(%esp)
    leal    40(%esp), %eax
    movl    %eax, (%esp)
    call    _ZN4PairC1Eii
    movl    $2, 24(%esp)
    movl    $2, 28(%esp)
    leal    32(%esp), %eax
    movl    %eax, 4(%esp)
    leal    40(%esp), %eax
    movl    %eax, (%esp)
    call    _ZneI4PairS0_EbRKT_RKT0_
    testb    %al, %al
    jne    .L8
    movl    $_ZZ4mainE19__PRETTY_FUNCTION__, 12(%esp)
    movl    $28, 8(%esp)
    movl    $.LC0, 4(%esp)
    movl    $.LC1, (%esp)
    call    __assert_fail
.L8:
    movl    24(%esp), %edx
    movl    28(%esp), %eax
    cmpl    %eax, %edx
    je    .L9
    movl    $_ZZ4mainE19__PRETTY_FUNCTION__, 12(%esp)
    movl    $29, 8(%esp)
    movl    $.LC0, 4(%esp)
    movl    $.LC2, (%esp)
    call    __assert_fail
.L9:
    leal    24(%esp), %eax
    movl    %eax, 4(%esp)
    leal    32(%esp), %eax
    movl    %eax, (%esp)
    call    _ZeqI4PairiEbRKT_RKT0_
    testb    %al, %al
    jne    .L10
    movl    $_ZZ4mainE19__PRETTY_FUNCTION__, 12(%esp)
    movl    $30, 8(%esp)
    movl    $.LC0, 4(%esp)
    movl    $.LC3, (%esp)
    call    __assert_fail
.L10:
    leal    40(%esp), %eax
    movl    %eax, 4(%esp)
    leal    28(%esp), %eax
    movl    %eax, (%esp)
    call    _ZeqIi4PairEbRKT_RKT0_
    testb    %al, %al
    jne    .L11
    movl    $_ZZ4mainE19__PRETTY_FUNCTION__, 12(%esp)
    movl    $31, 8(%esp)
    movl    $.LC0, 4(%esp)
    movl    $.LC4, (%esp)
    call    __assert_fail
.L11:
    movl    $0, %eax
    leave
    .cfi_restore 5
    .cfi_def_cfa 4, 4
    ret
    .cfi_endproc
.LFE6:
    .size    main, .-main
    .section    .text._ZneI4PairS0_EbRKT_RKT0_,"axG",@progbits,_ZneI4PairS0_EbRKT_RKT0_,comdat
    .weak    _ZneI4PairS0_EbRKT_RKT0_
    .type    _ZneI4PairS0_EbRKT_RKT0_, @function
_ZneI4PairS0_EbRKT_RKT0_:
.LFB7:
    .cfi_startproc
    pushl    %ebp
    .cfi_def_cfa_offset 8
    .cfi_offset 5, -8
    movl    %esp, %ebp
    .cfi_def_cfa_register 5
    subl    $24, %esp
    movl    12(%ebp), %eax
    movl    %eax, 4(%esp)
    movl    8(%ebp), %eax
    movl    %eax, (%esp)
    call    _ZeqI4PairS0_EbRKT_RKT0_
    xorl    $1, %eax
    leave
    .cfi_restore 5
    .cfi_def_cfa 4, 4
    ret
    .cfi_endproc
.LFE7:
    .size    _ZneI4PairS0_EbRKT_RKT0_, .-_ZneI4PairS0_EbRKT_RKT0_
    .section    .text._ZeqI4PairiEbRKT_RKT0_,"axG",@progbits,_ZeqI4PairiEbRKT_RKT0_,comdat
    .weak    _ZeqI4PairiEbRKT_RKT0_
    .type    _ZeqI4PairiEbRKT_RKT0_, @function
_ZeqI4PairiEbRKT_RKT0_:
.LFB8:
    .cfi_startproc
    pushl    %ebp
    .cfi_def_cfa_offset 8
    .cfi_offset 5, -8
    movl    %esp, %ebp
    .cfi_def_cfa_register 5
    pushl    %esi
    pushl    %ebx
    subl    $32, %esp
    .cfi_offset 6, -12
    .cfi_offset 3, -16
    movl    $0, %ebx
    movl    12(%ebp), %eax
    movl    (%eax), %eax
    movl    $0, 8(%esp)
    movl    %eax, 4(%esp)
    leal    -16(%ebp), %eax
    movl    %eax, (%esp)
    call    _ZN4PairC1Eii
    movl    $1, %esi
    leal    -16(%ebp), %eax
    movl    %eax, 4(%esp)
    movl    8(%ebp), %eax
    movl    %eax, (%esp)
    call    _ZltRK4PairS1_
    xorl    $1, %eax
    testb    %al, %al
    je    .L16
    movl    12(%ebp), %eax
    movl    (%eax), %eax
    movl    $0, 8(%esp)
    movl    %eax, 4(%esp)
    leal    -24(%ebp), %eax
    movl    %eax, (%esp)
    call    _ZN4PairC1Eii
    movl    $1, %ebx
    movl    8(%ebp), %eax
    movl    %eax, 4(%esp)
    leal    -24(%ebp), %eax
    movl    %eax, (%esp)
    call    _ZltRK4PairS1_
    xorl    $1, %eax
    testb    %al, %al
    je    .L16
    movl    $1, %eax
    jmp    .L17
.L16:
    movl    $0, %eax
.L17:
    testb    %bl, %bl
    movl    %esi, %edx
    testb    %dl, %dl
    addl    $32, %esp
    popl    %ebx
    .cfi_restore 3
    popl    %esi
    .cfi_restore 6
    popl    %ebp
    .cfi_restore 5
    .cfi_def_cfa 4, 4
    ret
    .cfi_endproc
.LFE8:
    .size    _ZeqI4PairiEbRKT_RKT0_, .-_ZeqI4PairiEbRKT_RKT0_
    .section    .text._ZeqIi4PairEbRKT_RKT0_,"axG",@progbits,_ZeqIi4PairEbRKT_RKT0_,comdat
    .weak    _ZeqIi4PairEbRKT_RKT0_
    .type    _ZeqIi4PairEbRKT_RKT0_, @function
_ZeqIi4PairEbRKT_RKT0_:
.LFB9:
    .cfi_startproc
    pushl    %ebp
    .cfi_def_cfa_offset 8
    .cfi_offset 5, -8
    movl    %esp, %ebp
    .cfi_def_cfa_register 5
    pushl    %esi
    pushl    %ebx
    subl    $32, %esp
    .cfi_offset 6, -12
    .cfi_offset 3, -16
    movl    $0, %ebx
    movl    8(%ebp), %eax
    movl    (%eax), %eax
    movl    $0, 8(%esp)
    movl    %eax, 4(%esp)
    leal    -16(%ebp), %eax
    movl    %eax, (%esp)
    call    _ZN4PairC1Eii
    movl    $1, %esi
    movl    12(%ebp), %eax
    movl    %eax, 4(%esp)
    leal    -16(%ebp), %eax
    movl    %eax, (%esp)
    call    _ZltRK4PairS1_
    xorl    $1, %eax
    testb    %al, %al
    je    .L22
    movl    8(%ebp), %eax
    movl    (%eax), %eax
    movl    $0, 8(%esp)
    movl    %eax, 4(%esp)
    leal    -24(%ebp), %eax
    movl    %eax, (%esp)
    call    _ZN4PairC1Eii
    movl    $1, %ebx
    leal    -24(%ebp), %eax
    movl    %eax, 4(%esp)
    movl    12(%ebp), %eax
    movl    %eax, (%esp)
    call    _ZltRK4PairS1_
    xorl    $1, %eax
    testb    %al, %al
    je    .L22
    movl    $1, %eax
    jmp    .L23
.L22:
    movl    $0, %eax
.L23:
    testb    %bl, %bl
    movl    %esi, %edx
    testb    %dl, %dl
    addl    $32, %esp
    popl    %ebx
    .cfi_restore 3
    popl    %esi
    .cfi_restore 6
    popl    %ebp
    .cfi_restore 5
    .cfi_def_cfa 4, 4
    ret
    .cfi_endproc
.LFE9:
    .size    _ZeqIi4PairEbRKT_RKT0_, .-_ZeqIi4PairEbRKT_RKT0_
    .section    .text._ZeqI4PairS0_EbRKT_RKT0_,"axG",@progbits,_ZeqI4PairS0_EbRKT_RKT0_,comdat
    .weak    _ZeqI4PairS0_EbRKT_RKT0_
    .type    _ZeqI4PairS0_EbRKT_RKT0_, @function
_ZeqI4PairS0_EbRKT_RKT0_:
.LFB10:
    .cfi_startproc
    pushl    %ebp
    .cfi_def_cfa_offset 8
    .cfi_offset 5, -8
    movl    %esp, %ebp
    .cfi_def_cfa_register 5
    subl    $8, %esp
    movl    12(%ebp), %eax
    movl    %eax, 4(%esp)
    movl    8(%ebp), %eax
    movl    %eax, (%esp)
    call    _ZltRK4PairS1_
    xorl    $1, %eax
    testb    %al, %al
    je    .L28
    movl    8(%ebp), %eax
    movl    %eax, 4(%esp)
    movl    12(%ebp), %eax
    movl    %eax, (%esp)
    call    _ZltRK4PairS1_
    xorl    $1, %eax
    testb    %al, %al
    je    .L28
    movl    $1, %eax
    jmp    .L29
.L28:
    movl    $0, %eax
.L29:
    leave
    .cfi_restore 5
    .cfi_def_cfa 4, 4
    ret
    .cfi_endproc
.LFE10:
    .size    _ZeqI4PairS0_EbRKT_RKT0_, .-_ZeqI4PairS0_EbRKT_RKT0_
    .section    .rodata
    .type    _ZZ4mainE19__PRETTY_FUNCTION__, @object
    .size    _ZZ4mainE19__PRETTY_FUNCTION__, 11
_ZZ4mainE19__PRETTY_FUNCTION__:
    .string    "int main()"
    .ident    "GCC: (Ubuntu 4.8.2-19ubuntu1) 4.8.2"
    .section    .note.GNU-stack,"",@progbits


Так кто же мы такие и куда движемся. Студенты, коллеги, зачем? Чёрный ящик, игральный автомат, русская рулетка. Почему вас это так заинтересовало. Бред ли? Нет, я компилятор. Понять значит предвидеть. Задумаемся. Пятница, выходной, понедельник. Головоломка. Для чего? Польза, генератор, строка. Дело было вечером, делать было нечего. Галка села на заборе, Кот забрался на чердак. Тут сказал ребятам Боря Просто так. А в-четвертых — наша мама Отправляется в полет, Потому что наша мама Называется — пилот!


А теперь серьёзно, самая неприятная часть С++ это его перегруженность разнообразными правилами. Игра в "Вальяжного профессора" и "Шустрого студента" (для тех кто не понял прочтите документ) не имеет ничего общего с практикой. Составление общей аналитической картины из разрозненных деталей напоминает фразу "опасно быть недоучкой".
Цитирую документ:

3) Я почему-то сейчас понял, что если пять лет писать компиляторы, то сходишь с ума

С ума сходят потому, что мозг стремится построить целостную картину, но при данном подходе к обучению поступающей на обработку информации для этого явно недостаточно. Компилятор каждый раз генерирует одно и тоже, в нём нет магии, только жёсткие правила. С++ это вообще не интеллектуальный язык, иначе говоря весь интеллект заложен только в том, что пишет сам программист, за него ничего не додумывается.

Кто умеет, тот делает. Кто не умеет учит. А кто не умеет даже учить, руководит. Всегда нужно стремиться стать руководителем.
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.