Công cụ bảo vệ mã nguồn .NET mạnh nhất, không thể unpack, miễn phí cho các khách hàng đầu tiên đăng ký.
Từ 1 tới 7 trên tổng số 7 kết quả

Đề tài: Container và Iterator tự tạo, có nhiều thắc mắc!

  1. #1
    Ngày gia nhập
    12 2015
    Nơi ở
    Đà Nẵng
    Bài viết
    503

    Mặc định Container và Iterator tự tạo, có nhiều thắc mắc!

    Mình muốn tạo 1 container giống vector và iterator. Container của mình là 1 mảng char cài đặt bằng vector "vch", ta chỉ quan tâm đến giá trị char tại các chỉ số chẵn, tại các chỉ số lẻ đều là 0, size() của nó được tính bằng 1/2 "vch.size()". Đây là những gì mình làm được
    C++ Code:
    1. #include <iostream>
    2. #include <vector>
    3. #include <algorithm>
    4.  
    5. namespace std
    6. {
    7.     class Step2Array
    8.     {
    9.     private:
    10.         vector<char> vch;
    11.     public:
    12.         class iterator;
    13.         void push_back(int n)
    14.         {
    15.             vch.push_back(n);
    16.             vch.push_back(0);
    17.         }
    18.         size_t size()
    19.         {
    20.             return vch.size() / 2; 
    21.         }
    22.         Step2Array::iterator begin()
    23.         {
    24.             return Step2Array::iterator(this, 0);
    25.         }
    26.         Step2Array::iterator end()
    27.         {
    28.             return Step2Array::iterator(this, size());
    29.         }
    30.         class iterator
    31.         {
    32.         private:
    33.             Step2Array* arr;
    34.             int pos;
    35.         public:
    36.             iterator(){}
    37.             iterator(Step2Array* arr, int pos) : arr(arr), pos(pos){}
    38.             iterator& operator++(int)
    39.             {
    40.                 pos++;
    41.                 return *this;
    42.             }
    43.             iterator& operator++()
    44.             {
    45.                 pos++;
    46.                 return *this;
    47.             }
    48.             int operator*()
    49.             {
    50.                 return arr->vch[pos*2];
    51.             }
    52.             bool operator==(iterator it)
    53.             {
    54.                 return arr == it.arr && pos == it. pos;
    55.             }
    56.             bool operator!=(iterator it)
    57.             {
    58.                 return !(*this == it);
    59.             }
    60.         };
    61.     };
    62. }
    63.  
    64. int main(int argc, char *argv[])
    65. {
    66.     std::Step2Array arr;
    67.     arr.push_back(2);
    68.     arr.push_back(3);
    69.     arr.push_back(5);
    70.     arr.push_back(7);
    71.     arr.push_back(11);
    72.     arr.push_back(13);
    73.     arr.push_back(17);
    74.     std::Step2Array::iterator begin, end;
    75.     begin = arr.begin();
    76.     end = arr.end();
    77.     while (begin != end) {
    78.         std::cout << *begin <<"\n";
    79.         begin++;
    80.     }
    81.     for (int i : arr) {
    82.         std::cout << i << ".\n";
    83.     }
    84.     //std::cout << max_element(arr.begin(), arr.end()) << "\n";
    85.     //sort(arr.begin(), arr.end());
    86. }/* kết quả là
    87. 2
    88. 3
    89. 5
    90. 7
    91. 11
    92. 13
    93. 17
    94. 2.
    95. 3.
    96. 5.
    97. 7.
    98. 11.
    99. 13.
    100. 17.
    101. */
    Cái mình muốn là có thể sử dụng các hàm có tham số kiểu iterator như hàm sort, max_element v.v, hỏi phải làm thế nào?Cảm ơn bạn đã đọc
    Công cụ bảo vệ mã nguồn .NET mạnh nhất hiện tại, miễn phí cho các khách hàng đầu tiên đăng ký.

  2. #2
    Ngày gia nhập
    12 2015
    Nơi ở
    Đà Nẵng
    Bài viết
    503

    Mình được biết "std::iterator" bị phản đối (deprecated) và sẽ bị gở bỏ, vậy mong muốn của mình còn thực hiện được không?

  3. #3
    Ngày gia nhập
    02 2014
    Nơi ở
    TP.HCM
    Bài viết
    929

    Vẫn thực hiện được như thường thôi. Có điều là không rõ bạn định thay đổi (hoặc viết đè) các hàm sort, max_element của thư viện <algorithm> hay bạn định viết các hàm đó như là thành phần của lớp Step2Array.

  4. #4
    Ngày gia nhập
    12 2015
    Nơi ở
    Đà Nẵng
    Bài viết
    503

    Mình muốn dùng luôn hàm "sort", "max_element",... của <algorithm> mà không ghi đè, thay đổi hay viết mới gì cả,
    tại mình thấy hàm "sort" có tham số kiểu iterator nên mình nghĩ nó cũng sẽ chạy với lớp iterator tự tạo của mình, nhưng khi chạy thử thì nó báo thiếu value_type gì đó
    Tóm lại, mình phải code Step2Array và Step2Array::iterator như thế nào để khi gọi sort,... của <algorithm> nó cho ra kết quả đúng


    Đã được chỉnh sửa lần cuối bởi khoaph : 11-08-2020 lúc 07:33 PM.

  5. #5
    Ngày gia nhập
    02 2014
    Nơi ở
    TP.HCM
    Bài viết
    929

    Có 2 cách làm chuyện này.
    1: Như mã bạn viết, chỉ cần thêm hàm sort trong namespace std riêng của bạn. Bạn cần viết mã cho hàm sort này, Hàm sort của <algorithm> sử dụng đối số bình thường. Thật ra đây là hạ sách, đúng hơn là mẹo vặt vì nó chẳng qua đánh lừa về ngữ nghĩa mà thôi.
    2: Bạn cài đặt hàng loạt các bản mẫu (template) các lớp phù hợp với các đối số của hàm sort trong <algorithm>. Đây là cách căn cơ và tốn nhiều công sức, mai mốt chúng ta tiếp tục.

    - - - Nội dung đã được cập nhật ngày 12-08-2020 lúc 02:03 PM - - -

    Bạn xem chỉnh sửa mã này
    C++ Code:
    1. #include <iostream>     // std::cout
    2. #include <algorithm>    // std::sort
    3. #include <vector>       // std::vector
    4. #include <time.h>
    5. using std::vector;
    6.  
    7. class Step2Array
    8. {
    9. private:
    10.     vector<int> m_vtChar1;      // Vector lưu mảng chết - dùng cho các công việc khác
    11.     vector<int> m_vtChar2;      // Lưu mảng dùng cho hàm sort của <algorithm>
    12.  
    13. public:
    14.     void push_back(int n)
    15.     {
    16.         m_vtChar1.push_back(n);
    17.         m_vtChar1.push_back(0);
    18.  
    19.         m_vtChar2.push_back(n);     // Nhập vào
    20.     }
    21.     size_t size() { return m_vtChar2.size(); }
    22.     vector<int>::iterator begin() { return m_vtChar2.begin(); }
    23.     vector<int>::iterator end() { return m_vtChar2.end(); }
    24.    
    25.     static bool incsort(int i, int j) { return (i<j); }     // Sắp xếp tăng - mặc định của sort
    26.     static bool dessort(int i, int j) { return (i>j); }     // Sắp xếp giảm
    27. };
    28.  
    29. int main()
    30. {
    31.     // Tạo mẫu thử
    32.     srand((unsigned int)time(0));
    33.     Step2Array  arr;
    34.     for (int i = rand() % 5 + 5; i >= 0; i--)
    35.         arr.push_back(rand() % 50);
    36.     // In mảng
    37.     for (int i : arr)
    38.         std::cout << i << ".\n";
    39.     std::cout << "\n";
    40.     // Sắp xếp tăng
    41.     std::sort(arr.begin(), arr.end());
    42.     for (int i : arr)
    43.         std::cout << i << ".\n";
    44.     std::cout << "\n";
    45.     // Sắp xếp giảm
    46.     std::sort(arr.begin(), arr.end(), arr.dessort);
    47.     for (int i : arr)
    48.         std::cout << i << ".\n";
    49.     std::cout << "\n";
    50.  
    51.     return 0;
    52. }
    Attached Thumbnails Attached Thumbnails New Bitmap Image.png  

  6. #6
    Ngày gia nhập
    12 2015
    Nơi ở
    Đà Nẵng
    Bài viết
    503

    Mặc định Container và Iterator tự tạo, có nhiều thắc mắc!

    Trích dẫn Nguyên bản được gửi bởi MHoang Xem bài viết
    Có 2 cách làm chuyện này.
    1: Như mã bạn viết, chỉ cần thêm hàm sort trong namespace std riêng của bạn. Bạn cần viết mã cho hàm sort này, Hàm sort của <algorithm> sử dụng đối số bình thường. Thật ra đây là hạ sách, đúng hơn là mẹo vặt vì nó chẳng qua đánh lừa về ngữ nghĩa mà thôi.
    2: Bạn cài đặt hàng loạt các bản mẫu (template) các lớp phù hợp với các đối số của hàm sort trong <algorithm>. Đây là cách căn cơ và tốn nhiều công sức, mai mốt chúng ta tiếp tục.

    - - - Nội dung đã được cập nhật ngày 12-08-2020 lúc 02:03 PM - - -

    Bạn xem chỉnh sửa mã này
    C++ Code:
    1. #include <iostream>     // std::cout
    2. #include <algorithm>    // std::sort
    3. #include <vector>       // std::vector
    4. #include <time.h>
    5. using std::vector;
    6.  
    7. class Step2Array
    8. {
    9. private:
    10.     vector<int> m_vtChar1;      // Vector lưu mảng chết - dùng cho các công việc khác
    11.     vector<int> m_vtChar2;      // Lưu mảng dùng cho hàm sort của <algorithm>
    12.  
    13. public:
    14.     void push_back(int n)
    15.     {
    16.         m_vtChar1.push_back(n);
    17.         m_vtChar1.push_back(0);
    18.  
    19.         m_vtChar2.push_back(n);     // Nhập vào
    20.     }
    21.     size_t size() { return m_vtChar2.size(); }
    22.     vector<int>::iterator begin() { return m_vtChar2.begin(); }
    23.     vector<int>::iterator end() { return m_vtChar2.end(); }
    24.    
    25.     static bool incsort(int i, int j) { return (i<j); }     // Sắp xếp tăng - mặc định của sort
    26.     static bool dessort(int i, int j) { return (i>j); }     // Sắp xếp giảm
    27. };
    28.  
    29. int main()
    30. {
    31.     // Tạo mẫu thử
    32.     srand((unsigned int)time(0));
    33.     Step2Array  arr;
    34.     for (int i = rand() % 5 + 5; i >= 0; i--)
    35.         arr.push_back(rand() % 50);
    36.     // In mảng
    37.     for (int i : arr)
    38.         std::cout << i << ".\n";
    39.     std::cout << "\n";
    40.     // Sắp xếp tăng
    41.     std::sort(arr.begin(), arr.end());
    42.     for (int i : arr)
    43.         std::cout << i << ".\n";
    44.     std::cout << "\n";
    45.     // Sắp xếp giảm
    46.     std::sort(arr.begin(), arr.end(), arr.dessort);
    47.     for (int i : arr)
    48.         std::cout << i << ".\n";
    49.     std::cout << "\n";
    50.  
    51.     return 0;
    52. }
    Cảm ơn bạn, nhưng code trên không đúng ý của mình. Thứ nhất mình không muốn tạo thêm mảng trung gian để dùng cho hàm "sort". Thứ hai mình muốn dùng Step2Array::iterator tự tạo chứ không phải vecror<int>::iterator
    Để rõ hơn, mình code chương trình khác
    Ch tr này tạo một mảng (container) các số nguyên có giá trị 0..15, cài đặt trên vector<char>, mỗi char chứa 2 số,( mỗi số chiếm 4 bit) và mình đã code các hàm push_back, set(short i, short n) để gán phần tử(nhóm 4 bit) thứ i giá trị n, get(short i) để lấy giá trị của phần tử thứ i
    C++ Code:
    1. #include <iostream>
    2. #include <vector>
    3. #include <algorithm>
    4.  
    5. namespace std
    6. {
    7.     class FourBitsArray
    8.     {
    9.     private:
    10.         std::vector<char> vch;
    11.         size_t sz = 0;
    12.     public:
    13.         size_t size()
    14.         {
    15.             return sz;
    16.         }
    17.         void push_back(short n)
    18.         {
    19.             n = n & 15;
    20.             short i = vch.size() - 1;
    21.             if (sz % 2 == 1) {
    22.                 vch[i] = vch[i] | n;
    23.             } else {
    24.                 vch.push_back(n<<4);
    25.             }
    26.             sz++;
    27.         }
    28.         void set(short i, short n)
    29.         {
    30.             if (i < 0 || i >= sz) {
    31.                 throw "Index out of range";
    32.             }
    33.             n = n & 15;
    34.             if (i % 2 == 0) {
    35.                 vch[i / 2] = vch[i / 2] & 15;
    36.                 vch[i / 2] = vch[i / 2] | (n << 4);
    37.             } else {
    38.                 vch[i / 2] = vch[i / 2] & 240;
    39.                 vch[i / 2] = vch[i / 2] | n;
    40.             }
    41.         }
    42.         short get(short i)
    43.         {
    44.             if (i < 0 || i >= sz) {
    45.                 throw "Index out of range";
    46.             }
    47.             if (i % 2 == 0) {
    48.                 return vch[i / 2] >> 4;
    49.             } else {
    50.                 return vch[i / 2] & 15;
    51.             }
    52.         }
    53.         class iterator
    54.         {
    55.            
    56.         };
    57.     };
    58. }
    59.  
    60. int main(int argc, char *argv[])
    61. {
    62.     std::FourBitsArray arr;
    63.     short n[11] = {2, 5, 3, 9, 12, 8, 15, 11, 4, 6, 7};
    64.     for (short i = 0; i < 11; i++) {
    65.         arr.push_back(n[i]);
    66.     }
    67.     for (short i = 0; i < arr.size(); i++) {
    68.         std::cout << arr.get(i) << " ";
    69.     }
    70.     std::cout << "\n";
    71.     arr.set(3, 13);
    72.     arr.set(8, 14);
    73.     for (short i = 0; i < arr.size(); i++) {
    74.         std::cout << arr.get(i) << " ";
    75.     }
    76.     std::cout << "\nsize()=" << arr.size() << "\n";
    77. }
    78. /*
    79. 2 5 3 9 12 8 15 11 4 6 7
    80. 2 5 3 13 12 8 15 11 14 6 7
    81. size()=11
    82. */
    83.  
    84. [Program finished]
    Hàm sort của <algorithm> đòi hỏi 2 tham số đầu là random access iterator, nên mình nghĩ nếu tạo được lớp FourBitsArray::iterator thích hợp, kế thừa random access iterator hay sao đó..., thì cũng có thể truyền nó vào hàm sort .
    Cái mình thắc mắc là mình có thể tạo lớp như vậy được không và nếu được thì làm như thế nào?

  7. #7
    Ngày gia nhập
    12 2015
    Nơi ở
    Đà Nẵng
    Bài viết
    503

    Mình không vội, mình sẽ đợi đến lúc có câu trả lời
    Công cụ bảo vệ mã nguồn .NET mạnh nhất hiện tại, miễn phí cho các khách hàng đầu tiên đăng ký.

Tags của đề tài này

Quyền hạn của bạn

  • Bạn không thể gửi đề tài mới
  • Bạn không thể gửi bài trả lời
  • Bạn không thể gửi các đính kèm
  • Bạn không thể chỉnh sửa bài viết của bạn