| Author |
Message |
< Erlang ~ How to move last element of list to first place |
| Hrvoje |
Posted: Sat Aug 29, 2009 5:13 pm |
|
|
|
Joined: 29 Aug 2009
Posts: 1
|
[1,2,3,4,5] -> [5,1,2,3,4].
Having lots of problems with this little problem. |
Last edited by Hrvoje on Sat Sep 05, 2009 9:18 am; edited 1 time in total |
|
| Back to top |
|
| rvirding |
Posted: Sat Aug 29, 2009 6:11 pm |
|
|
|
User
Joined: 30 Aug 2006
Posts: 452
Location: Stockholm, Sweden
|
Are you after the last element of the list then you you would want something like:
last([E]) -> E;
last([_|T]) -> last(T).
There is already a function last in the module lists.
list_length/1 is a function so you would have to call it with list_length(Y) in your code. It is also illegal to call a user function in the test of an if. |
|
|
| Back to top |
|
| baryluk |
Posted: Sat Aug 29, 2009 6:21 pm |
|
|
|
User
Joined: 05 Aug 2009
Posts: 48
|
list_length - 1 is illegal expression (substracting integer from atom), and will throw runtime exception, which will always evaluate to false in if.
Use list_length(L).
Second thing: there already is lists:last(L).
Thrid: your algorithm's isn't tailrecursive fully, and is also O(n^2).
This:
Code:
last([E]) -> E;
last([_|T]) -> last(T).
will be simpler and faster  |
_________________ Witold Baryluk
Erlang Training and Consulting Ltd
http://www.erlang-consulting.com |
|
| Back to top |
|
| baryluk |
Posted: Sat Aug 29, 2009 6:25 pm |
|
|
|
User
Joined: 05 Aug 2009
Posts: 48
|
rvirding wrote: It is also illegal to call a user function in the test of an if.
Good point. I rearly use if at all (always need to check in manual the sytnax for it). Pattern matching is enaugh in 98% cases.  |
_________________ Witold Baryluk
Erlang Training and Consulting Ltd
http://www.erlang-consulting.com |
|
| Back to top |
|
| Allan |
Posted: Sun Sep 06, 2009 5:04 am |
|
|
|
User
Joined: 29 Jun 2009
Posts: 30
|
Hrvoje wrote: [1,2,3,4,5] -> [5,1,2,3,4].
I would solve it for lists of arbitrary length with the following code:
Code:
list_rotate_right([]) -> [];
list_rotate_right([_] = List) -> List;
list_rotate_right(List) when is_list(List) ->
[lists:last(List) | lists:sublist(List, length(List) - 1)]
.
|
|
|
| Back to top |
|
| Sergio Salvato |
Posted: Mon Sep 07, 2009 12:56 pm |
|
|
|
Joined: 07 Sep 2009
Posts: 2
|
rot_right([]) -> [];
rot_right(L) when is_list(L) ->
[H | T] = lists:reverse(L),
[H | lists:reverse(T)]. |
|
|
| Back to top |
|
| baryluk |
Posted: Mon Sep 07, 2009 1:29 pm |
|
|
|
User
Joined: 05 Aug 2009
Posts: 48
|
Sergio Salvato wrote: rot_right([]) -> [];
rot_right(L) when is_list(L) ->
[H | T] = lists:reverse(L),
[H | lists:reverse(T)].
This is one of them most beautiful code I know. It can be easly be generalised to moving by any number of positions. It is O(n), and quite efficient (good cache locality). It is also usefull in imperative language to do rotation in place. I think it is nicly described in Jon Bentley's book "Programming Pearls", but not hard to invent it alone.  |
_________________ Witold Baryluk
Erlang Training and Consulting Ltd
http://www.erlang-consulting.com |
|
| Back to top |
|
| Mazen |
Posted: Mon Sep 07, 2009 1:45 pm |
|
|
|
User
Joined: 20 Jul 2006
Posts: 164
Location: London
|
I was going to post Sergio's way but after a few benchmarks of Allan's code I realized that for more then 2 million elements in a list the diff is so small that I just went and did something else instead
I personally prefer what Sergio posted, it is more clear imho. |
|
|
| Back to top |
|
| satishbhawra37 |
Posted: Fri Sep 25, 2009 6:19 pm |
|
|
|
Joined: 25 Sep 2009
Posts: 2
|
There is already a function last in the module lists.
There is already a function last in the module lists. |
_________________ Best hosting | website information |
|
| Back to top |
|
|
|