Chuyển đổi n chuỗi có độ dài m thành chuỗi m có độ dài n


16

Viết chương trình, với bất kỳ số chuỗi 'n' nào có độ dài 'm', trả về 'm' số chuỗi có độ dài 'n', với điều kiện này:

Mỗi chuỗi mới phải chứa các chữ cái ở cùng một chỉ mục của các chuỗi khác

Ví dụ, chuỗi đầu ra đầu tiên phải chứa chữ cái đầu tiên của tất cả các chuỗi đầu vào, chuỗi đầu ra thứ hai phải chứa chữ cái thứ hai của tất cả các chuỗi đầu vào, v.v.

Ví dụ (các số dưới các chữ cái là chỉ mục của chuỗi):

input: "car", "dog", "man", "yay"
        012    012    012    012
output: "cdmy", "aoaa", "rgny"
         0000    1111    2222

input: "money", "taken", "trust"
        01234    01234    01234
output: "mtt", "oar", "nku", "ees", "ynt"
         000    111    222    333    444

Giả sử rằng đầu vào là chính xác mọi lúc

Mã byte ngắn nhất sẽ thắng!

Biên tập:

Vì có nhiều ngôn ngữ lập trình và có thể có nhiều giải pháp khả thi cho từng ngôn ngữ đó, tôi sẽ đăng giải pháp ngắn nhất cho từng ngôn ngữ lập trình và người dùng đã cung cấp nó. Hãy tiếp tục viết mã!

Chỉnh sửa lại:

Nhờ người dùng Dennis tôi đã chèn một đoạn cho bảng xếp hạng.


2
Chúng tôi có một đoạn bảng xếp hạng mà bạn có thể thêm vào nội dung câu hỏi của mình. Không cần phải làm điều đó bằng tay.
Dennis


Tôi xin lỗi, tôi không biết nó được gọi là "hoán vị"
Tên đầu vào ở đây

6
Tôi không tin rằng những thách thức này là trùng lặp, bởi vì sự khác biệt liên quan đến chuyển vị rách rưới và một số xử lý khoảng trắng kỳ lạ trong câu hỏi khác. Mặc dù trong một số ngôn ngữ, các câu trả lời có thể rất giống nhau, tôi nghĩ rằng hầu hết chúng sẽ khác nhau đến mức không nên trùng lặp.
FryAmTheEggman

Câu trả lời:



9

Python, 36 29 byte

zip(*s) trả về một danh sách các bộ dữ liệu của mỗi ký tự, được hoán chuyển.

lambda s:map(''.join,zip(*s))

Dùng thử trực tuyến


Đầu ra cho biết "cdmy", "aoaa", "rgny", đó là một danh sách ["cdmy", "aoaa", "rgny"]hoặc một tuple("cdmy", "aoaa", "rgny")
mbomb007

map(''.join,zip(*s))cũng hoạt động cho chuyển đổi chuỗi (chỉ dành cho Python 2) và đối với Python 3, [*map(''.join,zip(*s))]afaik hoạt động
Value Ink

@ KevinLau-notKenny map(''.join,zip(*s))cũng hợp lệ cho Python 3 - chúng tôi cho phép các trình lặp / trình tạo thay cho danh sách theo mặc định.
Mego



7

PowerShell v2 +, 66 54 byte

param($n)for($x=0;$n[0][$x];$x++){-join($n|%{$_[$x]})}

Yo ... không map, không zip, không transpose, v.v., vì vậy chúng ta phải tự lăn lộn. Đạo cụ lớn cho @DarthTwon cho golf 12 byte.

Đưa đầu vào $n, thiết lập một forvòng lặp. Bộ khởi tạo $xthành0 , bài kiểm tra là liệu chúng ta có còn chữ cái trong từ $n[0][$x]hay không và chúng ta tăng $x++từng lần lặp.

Bên trong vòng lặp, chúng ta lấy một chuỗi các chuỗi của chúng ta, đưa nó vào một vòng lặp bên trong tạo ra ký tự thích hợp từ mỗi từ. Điều đó được gói gọn trong một -joinđể tạo thành một chuỗi và chuỗi đó được để lại trên đường ống. Khi kết thúc thực hiện, các chuỗi trên đường ống được in ngầm.

PS C:\Tools\Scripts\golfing> .\convert-n-strings.ps1 "Darth","-Twon","Rocks"
D-R
aTo
rwc
tok
hns

1
Thật tuyệt, đó là loại câu trả lời tôi muốn xem;) Đó là cách viết quá đơn giản ,thay vì nghĩ về câu trả lời
Tên đầu vào ở đây

Sử dụng một vòng lặp while có thể làm giảm thêm : param($n)$x=0;while($n[0][$x]){-join($n|%{$_[$x]});$x++}. Và không có lỗi ở đây: D
ThePoShWolf 12/07/2016

@DarthTwon Tuyệt vời. Hoặc, sử dụng một forvòng lặp cho hai người khác. ;-)
admBorkBork

Hmm ... tôi đã thử nó, nhưng không phải sau khi thực sự giảm whilevòng lặp của tôi . Làm tốt lắm thưa ông!
ThePoShWolf

Bạn có thể sử dụng Linq trong Powershell?
aloisdg nói Phục hồi lại

7

Vim, 37 36 tổ hợp phím

Tất cả các câu trả lời khác đều nhàm chán và sử dụng các nội dung đơn byte nhàm chán. Đây là một câu trả lời hóc búa thực hiện toàn bộ thủ công, trong một thứ thậm chí không phải là ngôn ngữ lập trình:

Gmaqqgg:s/./&<cr>d<C-v>`aGo<esc>pvGgJ@qq@q`adgg

Giải trình:

G                                   "move to the end of this line
     ma                             "And leave mark 'a' here
       qq                           "Start recording in register 'q'
         gg                         "Move to the beginning
           :s/./&<cr>               "Assert that there is atleast one character on this line
                      d             "Delete
                       <C-v>        "Blockwise
                            `a      "Until mark 'a'

    G                               "Move to the end of the buffer
     o<esc>                         "Open a newline below us
           p                        "And paste what we deleted
            vG                      "Visually select everything until the end
              gJ                    "And join these without spaces
                @q                  "Call macro 'q'. The first time, this will do nothing,
                                    "The second time, it will cause recursion.
                  q                 "Stop recording
                   @q               "Call macro 'q' to start it all

Bây giờ, mọi thứ đều tốt, nhưng bộ đệm có một số văn bản thừa. Vì vậy, chúng ta phải:

`a                              "Move to mark 'a'
  dgg                           "And delete everything until the first line



4

Võng mạc , 45 43 byte

Số lượng byte giả định mã hóa ISO 8859-1.

O$#`.(?<=(.+))|¶
$.1
!`(?<=(¶)+.*)(?<-1>.)+

Các nguồn cấp dữ liệu hàng đầu là đáng kể. Đầu vào và đầu ra là các danh sách kết thúc chuỗi nguồn có thể in của chuỗi ASCII (lưu ý rằng cả hai đều có một dòng cấp dữ liệu duy nhất).

Hãy thử trực tuyến!

Trong một thời gian, tôi biết rằng các khối hình chữ nhật hoán vị sẽ là một nỗi đau ở Retina (trong khi các hình vuông chuyển vị không quá tệ), nhưng thực sự chưa bao giờ thử. Giải pháp đầu tiên thực sự là một con số khổng lồ dài 110 byte, nhưng sau một vài thay đổi đáng kể trong cách tiếp cận, 45 byte kết quả cho đến nay không tệ như tôi nghi ngờ (nhưng vẫn ...). Giải thích sẽ theo ngày mai.

Giải trình

Giai đoạn 1: Sắp xếp

O$#`.(?<=(.+))|¶
$.1

Điều này thực hiện công việc chính là sắp xếp lại các ký tự trong đầu vào, nhưng cuối cùng nó làm rối tung sự phân tách thành các dòng. Thật thú vị, nếu chúng ta loại bỏ , chúng ta sẽ nhận được mã cần thiết để chuyển đổi một đầu vào vuông.

Các giai đoạn sắp xếp (được biểu thị bởi O) hoạt động như thế này: họ tìm thấy tất cả các trận đấu của regex đã cho (điều sau `), sau đó sắp xếp các trận đấu đó và đặt lại chúng vào những nơi tìm thấy các trận đấu. Khi điều đó xảy ra, regex này khớp với mọi ký tự đơn: không phải là dòng thông qua .(?<=(.*))thay thế và nguồn cấp dữ liệu thông qua . Do đó, nó sắp xếp tất cả các ký tự trong đầu vào. Phần thú vị hơn là những gì chúng được sắp xếp theo .

Các $tùy chọn kích hoạt một "loại theo" chế độ, trong đó mỗi trận đấu được thay thế bằng mẫu thay thế trên dòng thứ hai, sau đó được sử dụng để so sánh các trận đấu. Hơn nữa,# yêu cầu Retina chuyển đổi kết quả của sự thay thế thành một số nguyên và so sánh các số nguyên đó (thay vì coi chúng là các chuỗi).

Vì vậy, cuối cùng, chúng ta cần xem xét regex và sự thay thế. Nếu sự thay thế đầu tiên khớp (nghĩa là chúng ta đã khớp bất kỳ ký tự nào trong một trong các dòng), thì nó sẽ (?<=(.*))bắt mọi thứ theo ký tự đó trên dòng đó thành nhóm 1. Các $.1trong mẫu thay thế thay thế này với chiều dài của nhóm 1. Do đó, ký tự đầu tiên trong mỗi chuỗi trở thành 1, ký tự thứ hai trở thành 2, ký tự thứ ba trở thành 3vân vân. Bây giờ, rõ ràng làm thế nào điều này chuyển đổi một đầu vào vuông: tất cả các ký tự đầu tiên của dòng đến trước và tất cả kết thúc ở dòng trên cùng, sau đó tất cả các ký tự thứ hai kết thúc trong dòng thứ hai, v.v. Nhưng đối với các đầu vào hình chữ nhật này, chúng tôi cũng phù hợp với các nguồn cấp dữ liệu. Kể từ khi nhóm1không được sử dụng trong trường hợp này, sự thay thế là trống rỗng, nhưng với mục đích của #tùy chọn, điều này được xem xét 0. Điều đó có nghĩa là, tất cả các nguồn cấp dữ liệu được sắp xếp ở phía trước.

Vì vậy, bây giờ chúng ta có các ký tự theo thứ tự đầu tiên (ký tự đầu tiên của mỗi chuỗi, ký tự thứ hai của mỗi chuỗi, v.v.) và tất cả các nguồn cấp dữ liệu khi bắt đầu.

Giai đoạn 2: Trận đấu

!`(?<=(¶)+.*)(?<-1>.)+

Bây giờ chúng ta cần chia các ký tự thành các dòng có độ dài chính xác. Độ dài này tương ứng với số lượng dòng trong đầu vào ban đầu, tương ứng với số lượng dòng chúng ta có ở đầu chuỗi.

Việc chia tách được thực hiện ở đây với sự trợ giúp của giai đoạn khớp, đơn giản là tìm tất cả các kết quả khớp của biểu thức đã cho và sử dụng !tùy chọn để in các kết quả khớp đó (mặc định sẽ là đếm chúng thay thế). Vì vậy, mục tiêu của regex là khớp một dòng tại một thời điểm.

Chúng tôi bắt đầu bằng cách "đếm" số với cái nhìn (?<=(¶)*.*). Nó tạo ra một bản chụp trong nhóm 1cho mỗi nguồn cấp dữ liệu ở phía trước.

Sau đó, với mỗi lần chụp đó, chúng tôi khớp với một nhân vật (?<-1>.)+.


4

mã máy x86, 19 byte

Trong hex:

fc89d35651a401dee2fb91aa595e464a75f1c3

Đầu vào :: ECX# của chuỗi (n) , EDX: độ dài chuỗi riêng (m) , ESI: mảng của chuỗi đầu vào , EDI: bộ đệm nhận đầu ra của chuỗi. Mảng được coi là được định nghĩa như char src[n][m+1]cho đầu vào và char dst[m][n+1]đầu ra, và tất cả các chuỗi được kết thúc bằng NULL.

0:  fc                  cld
1:  89 d3               mov ebx,edx   ;EDX is the counter for the outer loop
_outer:
3:  56                  push esi
4:  51                  push ecx
_inner:
5:  a4                  movsb         ;[EDI++]=[ESI++]
6:  01 de               add esi,ebx   ;Same char, next string
8:  e2 fb               loop _inner   ;--ECX==0 => break
a:  91                  xchg eax,ecx  ;EAX=0
b:  aa                  stosb         ;NULL-terminate just completed string
c:  59                  pop ecx
d:  5e                  pop esi       ;First string,
e:  46                  inc esi       ;...next char
f:  4a                  dec edx
10: 75 f1               jnz _outer
12: c3                  ret

3

Brachylog , 5 byte

z:ca.

Yêu cầu một danh sách các chuỗi làm đầu vào, vd run_from_atom('z:ca.',["money":"taken":"trust"],Output).

Giải trình

z       Zip the strings in the Input list
 :ca.   output is the application of concatenation to each element of the zip

3

05AB1E, 3 byte

ø€J

Giải thích

     # implicit input, eg: ['car', 'dog', 'man', 'yay']
ø    # zip, producing [['c', 'd', 'm', 'y'], ['a', 'o', 'a', 'a'], ['r', 'g', 'n', 'y']]
 €J  # map join, resulting in ['cdmy', 'aoaa', 'rgny']

Dùng thử trực tuyến



2

JavaScript ES6, 48 46 byte

a=>[...a[0]].map((n,x)=>a.map(a=>a[x]).join``)

Tôi cảm thấy bị bỏ rơi, chúng tôi không có chức năng zip tích hợp. Cảm ơn nicael đã chỉ ra lỗi loại của tôi.

Sử dụng

(a=>[...a[0]].map((n,x)=>a.map(a=>a[x])))(["asd","dsa"]); //or whatever is above, might change due to edits

trả lại

["ad","ss","da"]

Ngoại lệ: TypeError: a [0] .map không phải là một chức năng
edc65

1
Bạn cần [...a[0]].map, vì a[0]không phải là một mảng.
nicael

@nicael cảm ơn. làm rối tung các loại. điều này chứng tỏ tại sao tôi không nên chơi golf vào sáng sớm.
charredgrass

@nicael Tôi .joined họ để khắc phục vấn đề đó.
charredgrass

1
join`` thay vì join('')để lưu 2 byte. Downvote rút lại
edc65

2

Tiện ích Bash + BSD, 27

sed s/./\&:/g|rs -c: -g0 -T

I / O thông qua các chuỗi phân tách dòng mới STDIN / STDOUT.

Bạn có thể cần phải cài đặt rsvới sudo apt install rshoặc tương tự. Hoạt động tốt trên OS X.

Các -Ttùy chọn để rsthực hiện nâng nặng của chuyển vị. Phần còn lại chỉ là định dạng:

  • Các sedlệnh đơn giản chèn :sau mỗi nhân vật
  • -c:chỉ định các cột đầu vào được :tách ra
  • -g0 chỉ định các cột đầu ra có phân tách chiều rộng bằng không

Nếu cách đọc trang của tôi rslà chính xác, thì những điều sau đây phải hoạt động với số điểm 12, nhưng thật không may, nó không hoạt động - xem ghi chú bên dưới:

rs -E -g0 -T

Ví dụ đầu ra:

$ printf "%s\n" car dog man yay |sed s/./\&:/g|rs -c: -g0 -T
cdmy
aoaa
rgny
$

Nếu đầu vào dự kiến ​​là tất cả ASCII có thể in được, thì :có thể thay thế bằng một số ký tự không thể in được, ví dụ 0x7 BEL.


Ghi chú

Tôi muốn hiểu lý do tại sao tôi không thể có -Etùy chọn để làm việc và thoát khỏi quá trình sedtiền xử lý. Tôi tìm thấy rsmã nguồn ở đây . Như bạn có thể thấy, đưa ra tùy chọn này đặt ONEPERCHARcờ. Tuy nhiên, không có gì trong mã thực sự kiểm tra trạng thái của cờ này. Vì vậy, tôi nghĩ rằng chúng ta có thể nói rằng mặc dù thực tế là tùy chọn được ghi lại, nhưng nó không được thực hiện.

Trong thực tế, tùy chọn này được ghi lại trong trang của Linux rs:

-E Coi mỗi ký tự của đầu vào là một mục mảng.

nhưng không phải phiên bản OS X.


2

PHP, 82 byte

function f($a){foreach($a as$s)foreach(str_split($s)as$i=>$c)$y[$i].=$c;return$y;}

mất và trả về một chuỗi các chuỗi

phá vỡ

function f($a)
{
    foreach($a as$s)                    // loop through array $a
        foreach(str_split($s)as$i=>$c)  // split string to array, loop through characters
            $y[$i].=$c;                 // append character to $i-th result string
    return$y;
}

ví dụ

$samples=[
    ["asd","dsa"], ["ad","ss","da"],
    ["car", "dog", "man", "yay"], ["cdmy", "aoaa", "rgny"],
    ["money", "taken", "trust"], ["mtt", "oar", "nku", "ees", "ynt"]
];
echo '<pre>';
while ($samples)
{
    echo '<b>in:</b> ';         print_r($x=array_shift($samples));
    echo '<b>out:</b> ';        print_r(f($x));
    echo '<b>expected:</b> ';   print_r(array_shift($samples));
    echo '<hr>';
}

2

APL, 3 byte

↓⍉↑

lấy các chuỗi đầu vào và biến chúng thành một ma trận char. hoán vị ma trận. chia lại các hàng của ma trận kết quả thành các chuỗi.



1

Toán học, 26 byte

""<>#&/@(Characters@#)&

Chức năng ẩn danh. Lấy danh sách chuỗi làm đầu vào và trả về danh sách chuỗi làm đầu ra. Ký tự Unicode là U + F3C7, đại diện \[Transpose]. Hoạt động bằng cách chuyển đổi thành ma trận ký tự, hoán vị và chuyển đổi trở lại danh sách chuỗi. Nếu định dạng đầu vào / đầu ra được kéo dài, thì một chuyển đổi 5 byte đơn giản sẽ hoạt động:

#&

+1 bạn đánh tôi với cú đấm! (Nhưng tôi không thể sử dụng biểu tượng Transpose.) Nhân tiện, tại sao chữ T không hiển thị trên màn hình? (Nó ở đó khi tôi sao chép mã của bạn sang Mathematica).
DavidC

@DavidC Ký tự Unicode nằm trong Vùng sử dụng riêng, được đánh dấu là một phần dành cho các ký tự độc quyền và do đó không được gán chính thức một glyph cũng như không hiển thị ở hầu hết các phông chữ. Phông chữ của Mathicala chỉ tình cờ hiển thị ký tự này dưới dạng siêu ký tự T và giải thích nó là một \[Transpose].
LegionMammal978

@DavidC Tại sao họ không sử dụng ?
Adám

@ Adám IDK, bạn phải hỏi Wolfram Research về điều đó, không phải tôi
LegionMammal978

@ LegionMammal978 Nah, tôi rất vui miễn là tôi có APL .
Adám

1

MATLAB / Octave, 4 byte

@(x)x'

Điều này xác định một chức năng ẩn danh. Định dạng đầu vào là ['car'; 'dog'; 'man'; 'yay'].

Hãy thử nó ở đây .


Định dạng nào là đầu vào cho giải pháp này? Tôi không nghĩ rằng nó sẽ làm việc với cách Matlab xử lý chuỗi nếu bạn cố gắng để nhập chúng theo một cách Matlabby, ví dụ f = @(x)x', f([{'abcd'},{'abcd'},{'abcd'}])kết quả đầu ra ans = 'abcd' 'abcd' 'abcd'
sintax

@sintax Định dạng đầu vào phải là một mảng char 2D, như trong ví dụ được liên kết trong câu trả lời. Bạn đang sử dụng một mảng ô của chuỗi (thu được bằng cách ghép các mảng ô đơn). Nó nên là : f(['abcd';'abcd';'abcd']). Tôi đã chỉnh sửa câu trả lời để chỉ định định dạng đầu vào
Luis Mendo

1

Haskell, 41 byte

f l=zipWith($)[map(!!n)|n<-[0..]]$l<$l!!0

Hoặc với một chút không khí:

f l = zipWith ($) [map (!! n) | n <- [0..]] $
                  l <$ (l !! 0)

Danh sách thứ hai là danh sách các từ lặp đi lặp lại độ dài của một từ thời gian. Trên mỗi danh sách các từ, chúng tôi chọn chữ cái thứ n của mỗi từ, đưa ra kết quả.


1
Không cần một chương trình đầy đủ, vì "chương trình" có nghĩa là "chương trình hoặc chức năng" , vì vậy một chức năng là đủ. Bạn có thể vượt qua và trả về một danh sách các chuỗi và do đó bỏ qua wordsunwords. Hơn nữa, map(\_->l)(l!!0)l<*l!!0, vì vậy nó sôi lên \l->zipWith($)[map(!!n)|n<-[0..]]$l<$l!!0.
nimi

Oh, cảm ơn tốt :) Tôi đang cập nhật.
Villou24

Rất tiếc, lỗi đánh máy: đó là l<$l!!0(lần đầu tiên sai, lần thứ hai đúng), nhưng dù sao bạn cũng đã hiểu đúng.
nimi

1

Lisp thông thường, 62 byte

(lambda(s)(apply'map'list(lambda(&rest x)(coerce x'string))s))

Các mapchức năng có một loại kết quả (ở đây list), một hàm f để áp dụng và một hoặc nhiều chuỗi s1 , ..., sn . Tất cả các chuỗi được lặp lại song song. Đối với mỗi bộ phần tử (e1, ..., en) được lấy từ các chuỗi đó, chúng tôi gọi (f e1 ... en) và kết quả được tích lũy trong một chuỗi loại mong muốn.

Chúng tôi lấy một danh sách các chuỗi, nói ("car" "dog" "man" "yay")và sử dụng applyđể gọi map. Chúng ta phải làm điều này để danh sách đầu vào được sử dụng như nhiều đối số hơn map. Chính xác hơn, điều này:

(apply #'map 'list fn '("car" "dog" "man" "yay"))

... tương đương với:

(map 'list f "car" "dog" "man" "yay")

Và vì các chuỗi là các chuỗi, chúng tôi lặp song song trên tất cả các ký tự đầu tiên, sau đó tất cả các ký tự thứ hai, v.v ... Ví dụ: lần lặp đầu tiên gọi f như sau:

(f #\c #\d #\m #\y)

Lambda ẩn danh lấy danh sách các đối số được đưa ra và buộc nó trở lại thành một chuỗi.



0

Ruby, 46 byte

Có lẽ là lần đầu tiên "chuỗi Ruby không phải là số" thực sự cắn tôi rất nhiều vì tôi phải ánh xạ chuỗi thành mảng trước khi xử lý. (Thông thường phải sử dụngString#chars không đủ mất byte, nhưng vì tôi cần ánh xạ chúng, nên nó còn nhiều hơn thế)

->s{s.map!(&:chars).shift.zip(*s).map &:join}

0

Clojure, 68 byte

#(map(fn[g](reduce(fn[a b](str a(nth b g)))""%))(range(count(% 0))))

Ánh xạ một hàm chỉ reduce(đi vào các phần tử của danh sách từng cái một và nối ký tự thứ n của chuỗi) trên phạm vi từ 0 đến độ dài của chuỗi đầu tiên.

Xem trực tuyến: https://ideone.com/pwhZ8e


0

C #, 53 byte

t=>t[0].Select((_,i)=>t.Aggregate("",(a,b)=>a+b[i]));

C # lambda ( Func) trong đó đầu ra là IList<string>và đầu ra là IEnumerable<string>. Tôi không biết làm thế nào để làm việc ziptrong ngôn ngữ khác nhưng tôi không thể tìm ra cách sử dụng ngôn ngữ của C # ở đây. Aggregatephù hợp với nhu cầu tốt. Không có chuyển vị trong C #, có một trong Excel nhưng tôi sẽ không sử dụng nó.

Hãy thử trực tuyến!

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.