ตัดเมทริกซ์เพื่อให้ได้ผลรวมที่ต้องการ


21

คำนิยาม

ได้รับเมทริกซ์Mของจำนวนเต็มไม่เป็นลบและจำนวนเต็มไม่เป็นลบkเรากำหนดFkเป็น "สับออก" ฟังก์ชั่นที่เอาแถวและคอลัมน์ในทุกMที่มีkk

ตัวอย่าง:

M=(615128985604)F5(M)=(1260)

งานของคุณ

ได้รับMและผลรวมเป้าหมายSงานของคุณคือการหาค่าที่เป็นไปได้ทั้งหมดของkดังกล่าวว่าผลรวมขององค์ประกอบที่เหลืออยู่ในFk(M)เท่ากับSS

ตัวอย่าง:

รับเมทริกซ์ข้างต้นMและS=9 :

  • k=5เป็นวิธีแก้ปัญหาเนื่องจากF5(M)=(1260)และ1+2+6+0=9
  • เป็นทางออกเดียวที่เป็นไปได้อื่น ๆ : F 1 ( M ) = ( 5 4 )และ 5 + 4 = 9k=1F1(M)=(54)5+4=9

ดังนั้นการส่งออกคาดว่าจะเป็น }{1,5}

คำอธิบายและกฎ

  • อินพุตรับประกันว่าจะยอมรับโซลูชันอย่างน้อยหนึ่งรายการ
  • ผลรวมขององค์ประกอบในเมทริกซ์เดิมรับประกันได้ว่าจะสูงกว่าSS
  • คุณอาจจะสมมติ 0 หมายความว่าเมทริกซ์ที่ว่างเปล่าจะไม่นำไปสู่การแก้ปัญหาS>0
  • ค่าของอาจถูกพิมพ์หรือคืนในลำดับใดก็ได้และในรูปแบบที่สมเหตุสมผลและไม่คลุมเครือk
  • คุณได้รับอนุญาตไม่ให้ซ้ำซ้อนผลลัพธ์ (เช่นหรือ[ 1 , 5 , 1 , 5 ]ถือว่าเป็นคำตอบที่ถูกต้องสำหรับตัวอย่างข้างต้น)[1,1,5,5][1,5,1,5]
  • นี่คือรหัสกอล์ฟ

กรณีทดสอบ

M = [[6,1,5],[1,2,8],[9,8,5],[6,0,4]]
S = 9
Solution = {1,5}

M = [[7,2],[1,4]]
S = 7
Solution = {4}

M = [[12,5,2,3],[17,11,18,8]]
S = 43
Solution = {5}

M = [[7,12],[10,5],[0,13]]
S = 17
Solution = {0,13}

M = [[1,1,0,1],[2,0,0,2],[2,0,1,0]]
S = 1
Solution = {2}

M = [[57,8,33,84],[84,78,19,14],[43,14,81,30]]
S = 236
Solution = {19,43,57}

M = [[2,5,8],[3,5,8],[10,8,5],[10,6,7],[10,6,4]]
S = 49
Solution = {2,3,4,7}

M = [[5,4,0],[3,0,4],[8,2,2]]
S = 8
Solution = {0,2,3,4,5,8}

การรักษาโครงสร้างดั้งเดิมของอินพุตอาร์เรย์ (เช่น[[1,5],[1],[5],[]]สำหรับกรณีทดสอบครั้งแรก) เป็นวิธีการที่ถูกต้องหรือไม่
Shaggy

@Shaggy ใช่ นั่นดูสมเหตุสมผล
Arnauld

คำตอบ:


10

K (ngn / k) , 39 ไบต์

{a@&y=x{+//x*(&/'b)&\:&/b:~x=y}/:a:,/x}

ลองออนไลน์!

ขอบคุณ @ Adámสำหรับคำอธิบายนี้ :

{}ฟังก์ชั่นxคือMและyคือS

,/x แบนM (นี่คือผู้สมัครk )

a: มอบหมายให้ a

x{}/: ใช้ฟังก์ชันต่อไปนี้กับแต่ละรายการในขณะที่ใช้Mเป็นอาร์กิวเมนต์ซ้ายคงที่ ( x):

  x=y เมทริกซ์บูลีนแสดงให้เห็นที่องค์ประกอบของMเท่ากับปัจจุบันkผู้สมัคร

  ~ ปฏิเสธว่า

  b: กำหนดให้กับ b

  &/ และลด (ค้นหาคอลัมน์ที่ไม่มีk )

  (... )&\: และสิ่งต่อไปนี้:

   &/'b และการลดลงของแต่ละแถว (ค้นหาแถวที่ไม่มีk )

  x* คูณMด้วยสิ่งนั้น

  +// ผลรวม

y= รายการ Booleans ที่ระบุว่าSเท่ากับผลรวมเหล่านั้น

& ดัชนีของ Trues

a@ ใช้สิ่งนั้นเพื่อจัดทำดัชนีลงในองค์ประกอบ (ตัวเลือกk )


อย่าลังเลที่จะแก้ไขคำอธิบาย
อดัม

อันตรายของคำอธิบายการคัดลอกวาง ...
อาจ

6

APL (Dyalog Unicode) , 35 33 28 ไบต์SBCS

-7 ขอบคุณ ngn

แลมบ์ดานิรนาม รับSเป็นอาร์กิวเมนต์ด้านซ้ายและMเป็นอาร์กิวเมนต์ที่ถูกต้อง

{⍵[⍸⍺=(+/∘,⍵×∧/∘.∧∧⌿)¨⍵≠⊂⍵]}

ลองออนไลน์!

{} "dfn" และเป็นอาร์กิวเมนต์ด้านซ้ายและขวา ( SและM ) ตามลำดับ:

⍵[... ] index Mพร้อมพิกัดต่อไปนี้:

  ⊂⍵ ล้อมMเพื่อใช้เป็นองค์ประกอบเดียว

  ⍵= เปรียบเทียบแต่ละองค์ประกอบ (เช่นkผู้สมัคร) ของMกับทั้งM

  (...  ใช้ฟังก์ชัน tacit ต่อไปนี้กับแต่ละรายการ:

   ∧⌿ แนวตั้งและการลดขนาด (ค้นหาคอลัมน์ที่ไม่มีตัวเลือกk )

∘.∧ ผลิตภัณฑ์คาร์ทีเซียนบูลีนด้วย:

    ∧/ แนวนอนและการลดขนาด (ค้นหาแถวที่ไม่มีตัวเลือกk )

   ⍵× คูณMกับหน้ากากนั้น

   +/∘, รวมเมทริกซ์แบบแบน

  ⍺= บูลีนระบุว่าSเท่ากับผลรวมเหล่านั้นหรือไม่

   ดัชนีที่เป็นจริง


1
{M[⍸⍺={+/,(∧⌿d)/M⌿⍨∧/d←M≠⍵}¨M←⍵]}
ngn

@ngn ขอบคุณ ฉันจะไม่ใช้ทั่วโลกเพราะมันทำให้การประเมินสับสน: - คุณจะจัดทำดัชนีMยังไงเมื่อยังไม่ได้สร้าง?
อดัม

ผ่านเป็นใน dfn ภายในเป็นอย่างเท่าเทียมกันทำให้เกิดความสับสนกับฉัน
NGN

{⍵[⍸⍺=+/¨(,⍵×∧/∘.∧∧⌿)¨⍵≠⊂⍵]}
NGN

@ngn ใช่ฉันต้องการทำอะไรแบบนั้น ขอบคุณ!
อดัม


5

เยลลี่ , 20 19 17 15 14 ไบต์

pZnⱮFȦ€€ḋFẹƓịF

นี่คือลิงก์ monadic ที่ใช้Mเป็นอาร์กิวเมนต์และอ่านSจาก STDIN

ลองออนไลน์!

มันทำงานอย่างไร

pZnⱮFȦ€€ḋFẹƓịF  Main link. Argument: M

 Z              Zip; transpose the rows and columns of M.
p               Take the Cartesian product of M and its transpose, yielding all pairs
                (r, c) of rows and columns of M.
    F           Flatten; yield the elements of M.
  nⱮ            Not equal map; for each element e of M, compare the elements of the
                pairs (r, c) with e.
     Ȧ€€        All each each; for each array of Booleans corresponding to an (r, c)
                pair, test if all of them are true.
         F      Flatten; yield the elements of M.
        ḋ       Take the dot product of each list of resulting Booleans and the
                elements of M.
           Ɠ    Read an integer S from STDIN.
          ẹ     Find all indices of S in the dot products.
             F  Flatten; yield the elements of M.
            ị   Retrieve the elements of the right at the indices from the left.


5

Haskell , 88 86 84 77 ไบต์

  • -2 ไบต์ต้องขอบคุณBWO
  • -7 ไบต์ขอบคุณTesseract
m!s=[k|k<-m>>=id,s==sum[x|r<-m,all(/=k)r,(i,x)<-zip[0..]r,all((/=k).(!!i))m]]

ตรวจสอบ testcases

คำอธิบาย

m ! s =                                         -- function !, taking m and s as input
    [k |                                        -- the list of all k's such that
        k <- m >>= id,                          -- * k is an entry of m
        s == sum                                -- * s equals the sum of
            [x |                                --     the list of x's such that
                r <- m,                         --     * r is a row of m
                all (/= k) r,                   --     * r does not contain k
                (i, x) <- zip [0 ..] r,         --     * i is a valid column index; also let x = r[i]
                all ((/= k) . (!! i)) m         --     * none of the rows contain k at index i
            ]
    ]

ควรจะพูดว่า "ฟังก์ชั่น f"?
Quintec

1
@Quintec แน่นอนควรมี แต่ฉันเปลี่ยนเป็น "function! เพื่อประหยัด 2 ไบต์ด้วยBWO
Delfad0r

5

Pyth ,  27 23 22 21  20 ไบต์

fqvzss.DRsxLTQ-I#TQs

ชุดทดสอบ!

ไม่ซ้ำซ้อน

มันทำงานอย่างไร?

fqvzss.DRsxLTQ-I#TQs     Full program.
f                  s     Flatten M and keep only those elements T which satisfy:
 qvzss.DRsxLTQ-I#TQ      The filtering function. Breakdown:
              -I#TQ      Discard the rows that contain T. More elaborate explanation:
                # Q         |-> In M, keep only those elements that are...
               I            |-> Invariant under (equal to themselves after...)
              -  T          |-> Removing T.
                         Let's call the result of this expression CR (chopped rows).
          xLTQ           Map over the rows M and retrieve all indices of T.
         s               Collect indices in 1D list (flatten). Call this I.
      .DR                For each row left in CR, remove the elements at indices in I.
    ss                   Sum all the elements of this matrix flattened.
 qvz                     And then finally check whether they equal S.


4

Perl 6 , 80 74 ไบต์

->\m,\s{grep {s==sum m[m.$_;[[Z](m).$_]]}o{*.grep(:k,!*.grep($_))},m[*;*]}

ลองออนไลน์!

คำอธิบาย

->\m,\s{...}  # Anonymous block taking arguments m and s
  grep {...}o{...},m[*;*]   # Filter matrix elements
                            # with combination of two functions
    *.grep(:k,!*.grep($_))  # (1) Whatever code returning matching rows
    s==sum m[               # (2) s equals sum of elements
      m.$_;                 #     in matched rows
      [                     #     (array supporting multiple iterations)
       [Z](m).$_            #     and matched columns (matched rows
                            #     of m transposed with [Z])
      ]
    ]

3

05AB1E , 21 ไบต์

²˜ʒQεZ+}øεZ<~}ø_*OO¹Q

ลองออนไลน์!

แต่หลังจากที่ผมเคยเขียนคำตอบนี้เราเห็นของเควิน ฉันเชื่อว่านี่แตกต่างอย่างมากดังนั้นฉันจึงโพสต์แยกต่างหาก สัญชาตญาณของฉันบอกว่าจำนวนไบต์ที่เหมาะสมคือประมาณ 18 ดังนั้นฉันจะต้องกลับมาดูอีกครั้งและดูว่าฉันจะทำอะไรได้อีก ด้วยรหัสปัจจุบันมันเป็นไปไม่ได้ที่จะเขียนชุดทดสอบ แต่ฉันได้ตรวจสอบกรณีทดสอบทั้งหมดด้วยตัวเองและผลลัพธ์ถูกต้อง

อัลกอริทึมการครอบตัด

k=5

M=(615128985604)

k

(001000001000)

MRสูงสุด(R)R

(112000112000)

MC(สูงสุด(C)-1) ||   C||~+

(113001113001)

010M

(000110000110)(000120000600)

หลังจากนั้นผลรวมของเมทริกซ์ที่ได้จะถูกคำนวณ


1
คำตอบที่ดี! ฉันรู้ว่าของฉันจะเล่นกอล์ฟได้อย่างแน่นอน ฉันมีความสุขมากพอที่จะใช้งานได้รวมถึงกรณีที่น่ารำคาญ[[1,1,0,1],[2,0,0,2],[2,0,1,0]]ซึ่งทำให้ฉันเมาจำนวน1(ซึ่งลบทุกคอลัมน์ .. ) ฉันมีหัวที่ต่ำกว่า 20 เล็กน้อยเช่นเดียวกับความเป็นไปได้ น่าเสียดายที่มีตัวสร้างสำหรับการฝึกอบรมแทบจะไม่ถึงแม้จะมีผลิตภัณฑ์เพิ่มเมื่อเร็ว ๆ นี้ สำหรับ1|2( 1 2~ใน 05AB1E synthax) ส่งผลให้ 3 นี้เป็นเพราะการlogical ORกระทำเช่นbinary ORเมื่อตัวเลขที่นอกเหนือ0/ 1มีส่วนเกี่ยวข้อง (ฉันคิดว่า / สมมติ)
Kevin Cruijssen

@KevinCruijssen โอ้คุณพูดถูก! แล้วเอกสารควรเขียนค่าที่เหมาะสมหรือไม่หรือตรรกะ ฉันจะต้องแก้ไขให้ถูกต้องในไม่ช้า อย่างไรก็ตาม, bitwise OR ควรทำงานได้ดีเช่นกัน มันจะถูกแทนที่ด้วย+ล่ะค่ะฉันเดาดังนั้นฉันหวังว่าจะมีปัญหากับมัน :) ไม่มี
นาย Xcoder

2

05AB1E (เดิม) , 27 26 ไบต์

˜ʒ©¹ε®å_}¹ζʒ®å_}ζ‚ζ€€OPOIQ

ไม่เรียงลำดับหรือไม่ซ้ำผลลัพธ์
ใช้งานได้เฉพาะในมรดก (สำหรับตอนนี้) เนื่องจากผลรวมแต่ละรายการดูเหมือนจะทำสิ่งแปลก ๆ เมื่อส่วนหนึ่งของรายการภายในเป็นจำนวนเต็มและรายการอื่น ๆ เป็นรายการ ..

ลองมันออนไลน์หรือตรวจสอบกรณีทดสอบทั้งหมด

คำอธิบาย:

˜              # Flatten the (implicit) matrix-input
               #  i.e. [[6,1,5],[1,2,8],[9,8,5],[6,0,4]] → [6,1,5,1,2,8,9,8,5,6,0,4]
 ʒ             # Filter this list by:
  ©            #  Store the current value in a register-variable
   ¹           #  Take the matrix-input
    ε   }      #  Map it to:
     ®å_       #   0 if the current number is in this row, 1 if not
               #    i.e. [[6,1,5],[1,2,8],[9,8,5],[6,0,4]] and 6 → [0,1,1,0]
   ¹           #  Take the matrix-input again
    ζ          #  Swap its rows and columns
               #   i.e. [[6,1,5],[1,2,8],[9,8,5],[6,0,4]] → [[6,1,9,6],[1,2,8,0],[5,8,5,4]]
     ʒ   }     #  Filter it by:
      ®å_      #   Only keep the inner lists that does not contain the current number
               #    i.e. [[6,1,9,6],[1,2,8,0],[5,8,5,4]] and 6 → [[1,2,8,0],[5,8,5,4]]
               #    i.e. [[1,2,2],[1,0,0],[0,0,1],[1,2,0]] and 1 → []
          ζ    #  After filtering, swap it's rows and columns back again
               #   i.e. [[1,2,8,0],[5,8,5,4]] → [[1,5],[2,8],[8,5],[0,4]]
   ‚ζ          #  Pair both lists together and zip them
               #   i.e. [0,1,1,0] and [[1,5],[2,8],[8,5],[0,4]]
               #    → [[0,[1,5]],[1,[2,8]],[1,[8,5]],[0,[0,4]]]
               #   i.e. [0,1,0] and [] → [[0,' '],[1,' '],[0,' ']]
              #  Map each inner list / value to:
      O       #   Sum each
               #    i.e. [[0,[1,5]],[1,[2,8]],[1,[8,5]],[0,[0,4]]]
               #     → [[0,6],[1,10],[1,13],[0,4]]
               #    i.e. [[0,' '],[1,' '],[0,' ']]
               #     → [[0,0],[1,0],[0,0]]
               #  (NOTE: For most test cases just `O` instead of `€€O` would be enough,
               #   but not if we removed ALL zipped inner lists for a number, like the 
               #   second example above with input [[1,1,0,1],[2,0,0,2],[2,0,1,0]] and 1)
        P      #  Now take the product of each inner list
               #   i.e. [[0,6],[1,10],[1,13],[0,4]] → [0,10,13,0]
         O     #  Then take the sum of those
               #   i.e. [0,10,13,0] → 23
          IQ   #  And only keep those that are equal to the number-input
               #   i.e. 23 and 9 → 0 (falsey), so it's removed from the flattened input


1

ถ่าน 33 ไบต์

FθFι⊞υκIΦυ⁼ηΣEθ∧¬№λιΣEλ∧¬№Eθ§πξιν

ลองออนไลน์! การเชื่อมโยงคือการใช้รหัสรุ่นที่ละเอียดและรวมถึงการขจัดข้อมูลซ้ำซ้อน คำอธิบาย:

FθFι⊞υκ

แผ่เข้าแถวแรกที่เข้ามาในรายการที่กำหนดไว้ล่วงหน้าqu

  υ                          Flattened array
 Φ                           Filter elements
       θ                     Input array
      E                      Map over rows
            ι                Current element
           λ                 Current row
          №                  Count matching elements
         ¬                   Logical Not
        ∧                    Logical And
               λ             Current row
              E              Map over columns
                    θ        Input array
                   E         Map over rows
                      π      Inner row
                       ξ     Column index
                     §       Inner element
                        ι    Current element
                  №          Count matching elements
                 ¬           Logical Not
                ∧            Logical And
                         ν   Current element
             Σ               Sum
     Σ                       Sum
    η                        Second input
   ⁼                         Equals
I                            Cast to string
                             Implicitly print each result on its own line

สำหรับแต่ละองค์ประกอบของรายการให้หาผลรวมของอาร์เรย์ แต่ถ้าแถวนั้นมีองค์ประกอบนั้นให้ใช้0แทนผลรวมของมันและเมื่อรวมแถวที่ไม่มีองค์ประกอบแล้วถ้าคอลัมน์นั้นมีองค์ประกอบอยู่ให้ใช้0แทนค่าของคอลัมน์ . นี่เป็นนักกอล์ฟที่ดีกว่าการกรององค์ประกอบออกไปเล็กน้อยเนื่องจาก Charcoal ไม่สามารถสรุปรายการที่ว่างเปล่าได้


1

ทำความสะอาด , 92 ไบต์

import StdEnv
$m s=[c\\r<-m,c<-r|sum[b\\a<-m|all((<>)c)a,b<-a&x<-[0..]|all(\u=u!!x<>c)m]==s]

ลองออนไลน์!

อธิบาย:

$ m s                       // the function $ of `m` and `s`
 = [                        // is equal to
  c                         // the value `c`
  \\ r <- m                 // for every row `r` in `m`
  , c <- r                  // for every value `c` in `r`
  | sum [                   // where the sum of
   b                        // the value `b`
   \\ a <- m                // for every row `a` in `m`
   | all ((<>)c) a          // where `c` isn't in `a`
   , b <- a                 // for every value `b` in `a`
   & x <- [0..]             // with every column index `x` from zero
   | all (\u = u!!x <> c) m // where `c` isn't in column `x`
  ] == s                    // equals `s`
 ]

1

MATLAB - 80 ไบต์

( แก้ไขแล้ว ) กระชับแล้ว:

function f(M,s);for k=M(:)';if sum(sum(M(~sum(M==k,2),~sum(M==k))))==s;k,end;end

และในเวอร์ชันที่ถูกพัฒนาอย่างสมบูรณ์:

function getthesum(M,s)

for k=M(:)'                         % For each element of M
    x = M==k ;                      % Index elements equal to "k"
    N = M( ~sum(x,2) , ~sum(x) ) ;  % New matrix with only the appropriate rows/columns
    if sum(sum(N))==s               % sum rows and columns and compare to "s"
        k                           % display "k" in console if "k" is valid
    end
end

ขอบคุณความคิดเห็นเพื่อเน้นความผิดพลาดครั้งแรกของฉัน โปรดทราบว่ารุ่นนี้ไม่ได้ทำซ้ำเอาท์พุท

เป็นไปได้ที่จะลดการซ้ำซ้อนของเอาต์พุตด้วยจำนวนไบต์ที่มากกว่า 5:

% This will only cycle through the unique elements of 'M' (85 bytes):

function f(M,s);for k=unique(M)';if sum(sum(M(~sum(M==k,2),~sum(M==k))))==s;k,end;end

1
kอาจเป็นองค์ประกอบใด ๆ ของเมทริกซ์
Dennis

@Dennis, โอ๊ะโอใช่แล้ว ... ฉันไม่ดีฉันจะแก้ไขให้ถูกต้องในวันนี้ ขอบคุณที่ชี้นำ
Hoki

1
@Arnauld ขออภัยฉันอยู่ในช่วงวันหยุด
Hoki
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.