2013-10-25 5 views
0

Допустим, у нас есть этот список '((4 (1 2)) (5 (5 5)) (7 (3 1)) (1 (2 3)))Возвращает второй элемент для каждого элемента в списке

Я пытаюсь написать что-л на схеме, чтобы получить второй элемент для каждого элемента в списке .. Таким образом, результат будет выглядеть '((1 2) (5 5) (3 1) (2 3))

У меня есть этот код до сих пор ..

(define (second list1) 
    (if (null? (cdr list1)) 
     (cdr (car list1)) 
     ((cdr (car list1))(second (cdr list1))))) 
+0

что не так с кодом? –

+0

Я получаю это..приложение: не процедура; ожидаемая процедура, которая может быть применена к аргументам : '((3 1)) аргументы ...: ' ((2 3)) – dionysosz

+0

Отформатируйте код разумным способом (т.е. строки, содержащие только парсеры) и проблема будет легче обнаружить. –

ответ

3

Вот простое решение:

(define (seconds lst) 
    (map cadr lst)) 

В общем, если вы хотите преобразовать каждый элемент списка, то можно перейти к map.

+1

Ничего себе !! Большое спасибо! Мне нужно много узнать о Scheme – dionysosz

+0

@ dionysosz. Если этот ответ сработал для вас, рассмотрите [его принятие] (http://meta.stackexchange.com/q/5234/225437). –

1

Все, что вам нужно сделать, это map встроенной функцией second на список lst:

(map second lst) 
1

Ваша ошибка в том, что вам не хватает оператора, может быть cons. Если вы посмотрите на следствии:

((cdr (car list1))(second (cdr list1))) 

Так Схема ожидает (корд (список автомобилей)), чтобы быть процедурой, так как он находится в позиции оператора в форме, но так как это не вы получите сообщение об ошибке. Кроме того, (cdr (car x)) == cdar не будет брать второй элемент в каждом элементе, кроме хвоста каждого элемента. cadar - это то, что вы ищете.

(define (second list1)00+ 
    (if (null? (cdr list1)) 
     (cons (cadar list1) '()) 
     (cons (cadar list1) (second (cdr list1))))) 

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

(define (second list1) 
    (if (null? list1) 
     '() 
     (cons (cadar list1) (second (cdr list1))))) 

Результат для списка будет то же самое. Существует процедура, называемая map. Он поддерживает несколько аргументов списка, но для одного из них:

(define (map fun lst) 
    (if (null? lst) 
     '() 
     (cons (fun (car lst)) (map fun (cdr lst))))) 

Похоже, что знакомы? Оба составляют список на основе каждого элемента, но map является общим. Таким образом, мы должны попытаться сделать (fun (car lst)) так же, как (cadar lst).

(define (second lst) 
    (map cadr lst)) ; (cadr (car x)) == (cadar x) 

У вас есть это. Chris beat me to it, но я хотел бы прокомментировать один из других ответов, который использует аббревиатуру second. Он определен в racket/base и библиотеке SRFI-1, но он не упоминается в последних отчетах Схемы. То есть для некоторых реализаций может потребоваться импортировать дополнительную библиотеку для ее работы.

+0

... и один из других ответов также имеет это, но также использует 'cadr', как ваше решение, а не синоним' second', но ваш пост, похоже, не обратил внимания на это, хотя это был самый быстрый пистолет на западе и был принят. ;-) –

+1

@ ChrisJester-Young Вы быстро :-), но я комментирую другой ответ, говоря о том, что вы не можете ожидать, что каждый make будет иметь «второй». – Sylwester

Смежные вопросы