Problem:
Score : 700 points

Problem Statement

Takahashi is playing with N cards.

The i-th card has an integer X_i on it.

Takahashi is trying to create as many pairs of cards as possible satisfying one of the following conditions:

The integers on the two cards are the same.

The sum of the integers on the two cards is a multiple of M.

Find the maximum number of pairs that can be created.

Note that a card cannot be used in more than one pair.

Constraints

2≦N≦10^5

1≦M≦10^5

1≦X_i≦10^5

Input

The input is given from Standard Input in the following format:

N M
X_1 X_2 ... X_N

Output

Print the maximum number of pairs that can be created.

Sample Input 1

7 5
3 1 4 1 5 9 2

Sample Output 1

3

Three pairs (3,2), (1,4) and (1,9) can be created.

It is possible to create pairs (3,2) and (1,1), but the number of pairs is not maximized with this.

Sample Input 2

15 10
1 5 6 10 11 11 11 20 21 25 25 26 99 99 99

Sample Output 2

6

Solution in Common Lisp (SBCL 1.1.14) (judge verdict: Accepted)

;; -*- coding: utf-8 -*-
(eval-when (:compile-toplevel :load-toplevel :execute)
  (defparameter OPT
    #+swank '(optimize (speed 3) (safety 2))
    #-swank '(optimize (speed 3) (safety 0) (debug 0)))
  #+swank (progn (ql:quickload '(:cl-debug-print :fiveam))
                 (shadow :run)
                 (use-package :fiveam))
  #-swank (set-dispatch-macro-character #\# #\> (lambda (s c p) (declare (ignore c p)) (read s nil (values) t))))
#+swank (cl-syntax:use-syntax cl-debug-print:debug-print-syntax)

;; BEGIN_INSERTED_CONTENTS
;; Scheme-style named let
(defmacro nlet (name args &body body)
  (labels ((ensure-list (x) (if (listp x) x (list x))))
    (let ((args (mapcar #'ensure-list args)))
      `(labels ((,name ,(mapcar #'car args) ,@body))
         (,name ,@(mapcar #'cadr args))))))

(declaim (ftype (function * (values fixnum &optional)) read-fixnum))
(defun read-fixnum (&optional (in *standard-input*))
  (declare #.OPT)
  (macrolet ((%read-byte ()
               `(the (unsigned-byte 8)
                     #+swank (char-code (read-char in nil #\Nul))
                     #-swank (sb-impl::ansi-stream-read-byte in nil #.(char-code #\Nul) nil))))
    (let* ((minus nil)
           (result (loop (let ((byte (%read-byte)))
                           (cond ((<= 48 byte 57)
                                  (return (- byte 48)))
                                 ((zerop byte) ; #\Nul
                                  (error "Read EOF or #\Nul."))
                                 ((= byte #.(char-code #\-))
                                  (setf minus t)))))))
      (declare ((integer 0 #.most-positive-fixnum) result))
      (loop
        (let* ((byte (%read-byte)))
          (if (<= 48 byte 57)
              (setq result (+ (- byte 48) (* 10 (the (integer 0 #.(floor most-positive-fixnum 10)) result))))
              (return (if minus (- result) result))))))))

(defmacro dbg (&rest forms)
  #+swank
  (if (= (length forms) 1)
      `(format *error-output* "~A => ~A~%" ',(car forms) ,(car forms))
      `(format *error-output* "~A => ~A~%" ',forms `(,,@forms)))
  #-swank (declare (ignore forms)))

(defmacro define-int-types (&rest bits)
  `(progn
     ,@(mapcar (lambda (b) `(deftype ,(intern (format nil "UINT~A" b)) () '(unsigned-byte ,b))) bits)
     ,@(mapcar (lambda (b) `(deftype ,(intern (format nil "INT~A" b)) () '(signed-byte ,b))) bits)))
(define-int-types 2 4 7 8 15 16 31 32 62 63 64)

(declaim (inline println))
(defun println (obj &optional (stream *standard-output*))
  (let ((*read-default-float-format* 'double-float))
    (prog1 (princ obj stream) (terpri stream))))

(defconstant +mod+ 1000000007)

;; Body

(defun main ()
  (declare #.OPT (inline sort))
  (let* ((n (read))
         (m (read))
         (xs (make-array n :element-type 'uint32))
         (mod-table (make-array m :element-type 'list :initial-element nil))
         (res 0))
    (declare (uint32 res))
    (dotimes (i n) (setf (aref xs i) (read-fixnum)))
    (setf xs (sort xs #'<))
    (loop for x across xs
          do (push x (aref mod-table (mod x m))))
    (labels ((frob (list pairs rest)
               (cond ((null list)
                      (values pairs rest))
                     ((null (cdr list))
                      (frob (cdr list) pairs (cons (car list) rest)))
                     (t (let ((num1 (car list))
                              (num2 (cadr list)))
                          (declare (uint32 num1 num2))
                          (if (= num1 num2)
                              (frob (cddr list) (cons num1 (cons num2 pairs)) rest)
                              (frob (cdr list) pairs (cons (car list) rest))))))))
      (loop for rem from 1 below m
            while (< rem (- m rem))
            do (multiple-value-bind (pairs1 rest1) (frob (aref mod-table rem) nil nil)
                 (multiple-value-bind (pairs2 rest2) (frob (aref mod-table (- m rem)) nil nil)
                   (declare (list pairs1 rest1 pairs2 rest2))
                   ;; guarantees |rest1| <= |rest2|
                   (let ((minlen (min (length rest1) (length rest2))))
                     (when (> (length rest1) minlen)
                       (rotatef pairs1 pairs2)
                       (rotatef rest1 rest2))
                     (incf res minlen)
                     (setf rest2 (nthcdr minlen rest2))
                     (dolist (_ rest2)
                       (unless (null pairs1)
                         (incf res)
                         (pop pairs1)))
                     (incf res (floor (length pairs1) 2))
                     (incf res (floor (length pairs2) 2))))))
      (incf res (floor (length (aref mod-table 0)) 2))
      (when (evenp m)
        (incf res (floor (length (aref mod-table (floor m 2))) 2)))
      (println res))))

#-swank(main)