Tạo dãy số ngẫu nhiên không trùng

Liên hệ QC

anhtuan1066

Thành viên gạo cội
Tham gia
10/3/07
Bài viết
5,802
Được thích
6,912
Trên diển đàn GPE đã có rất nhiều bài viết nói về vấn đề này!
Tôi cũng đã tham khảo rất nhiều code ở các trang nước ngoài nhưng thấy rằng hầu hết đều viết rất khó hiểu và dài dòng!
Trong 1 dịp tình cờ khi nghiên cứu về Dictionary Object, tôi nhận thấy rằng nó có khả năng làm được điều này mà code lại cực kỳ đơn giản
Thuật toán dựa vào định nghĩa của Dictionary có đoạn: Key là những phần tử duy nhất trong Keys
Tôi đã xây dựng code như sau:
PHP:
Function UniqueRandomNum(Bottom As Long, Top As Long, Amount As Long)
  'Application.Volatile '<--- Neu muon gia tri thay doi khi bam F9
  On Error Resume Next
  If Amount > Top - Bottom + 1 Then Amount = Top - Bottom + 1
  With CreateObject("Scripting.Dictionary")
    Do
      .Add Int(Rnd() * (Top - Bottom + 1)) + Bottom, ""
    Loop Until .Count = Amount
    UniqueRandomNum = WorksheetFunction.Transpose(.Keys)
  End With
End Function
Cú pháp hàm:
PHP:
=UniqueRandomNum(Số nhỏ, Số lớn, bao nhiêu số cần tạo)
Giả sử các bạn muốn tạo ra 30 số ngẩu nhiên không trùng nằm trong khoảng từ 1 đến 100, các bạn làm như sau:
- Quét chọn 30 cell tùy ý theo chiều dọc, chẳng hạn là A1:A30
- Gõ vào thanh Formula công thức =UniqueRandomNum(1,100,30)
- Bấm tổ hợp phím Ctrl + Shift + Enter
Hãy thí nghiệm với đoạn Test sau:
PHP:
Sub Test()
  Range("A1:A30").Value = UniqueRandomNum(1, 100, 30)
End Sub
--------------
Ghi chú: Dictionary Object còn làm được nhiều thứ khác nữa, chẳng hạn có thể xây dựng hàm trích lọc các phần tử duy nhất (ngẫu nhiên và duy nhất đã làm được, đương nhiên duy nhất sẽ càng dể hơn)
 

File đính kèm

Lần chỉnh sửa cuối:
Cái code của bạn cũng rất hay nhưng nó không tạo chuỗi số mới khi load lại hoặc thay đổi một giá trị ở ô khác
Bài đã được tự động gộp:


Bạn cho hỏi là làm sao để khi nó tự tạo ra một dãy số mới khi mình thay đổi một giá trị trong bảng (kiểu như hàm rand có sẵn vậy)
Trong code, tác giả đã tạm bỏ dòng này để hàm không tự động cập nhật
Mã:
Application.Volatile '<--- Neu muon gia tri thay doi khi bam F9
Bạn chọn nó là OK
 
Upvote 0
Trong code, tác giả đã tạm bỏ dòng này để hàm không tự động cập nhật
Mã:
Application.Volatile '<--- Neu muon gia tri thay doi khi bam F9
Bạn chọn nó là OK
Cám ơn bạn
Trong code, tác giả đã tạm bỏ dòng này để hàm không tự động cập nhật
Mã:
Application.Volatile '<--- Neu muon gia tri thay doi khi bam F9
Bạn chọn nó là OK
Đã chọn rồi mà không thấy tác dụng gì cả bạn ơi
 
Upvote 0
Mình có xem các bác hướng dẫn và làm file bốc thăm thi đấu loại trực tiếp cho môn Bida, anh em cần có thể lấy tham khảo, Bốc thăm ngẫu nhiên và điền tên vào Bảng thi đấu sẵn luôn nhé!
 

File đính kèm

Upvote 0
Trên diển đàn GPE đã có rất nhiều bài viết nói về vấn đề này!
Tôi cũng đã tham khảo rất nhiều code ở các trang nước ngoài nhưng thấy rằng hầu hết đều viết rất khó hiểu và dài dòng!
Trong 1 dịp tình cờ khi nghiên cứu về Dictionary Object, tôi nhận thấy rằng nó có khả năng làm được điều này mà code lại cực kỳ đơn giản
Thuật toán dựa vào định nghĩa của Dictionary có đoạn: Key là những phần tử duy nhất trong Keys
Tôi đã xây dựng code như sau:
PHP:
Function UniqueRandomNum(Bottom As Long, Top As Long, Amount As Long)
  'Application.Volatile '<--- Neu muon gia tri thay doi khi bam F9
  On Error Resume Next
  If Amount > Top - Bottom + 1 Then Amount = Top - Bottom + 1
  With CreateObject("Scripting.Dictionary")
    Do
      .Add Int(Rnd() * (Top - Bottom + 1)) + Bottom, ""
    Loop Until .Count = Amount
    UniqueRandomNum = WorksheetFunction.Transpose(.Keys)
  End With
End Function
Cú pháp hàm:
PHP:
=UniqueRandomNum(Số nhỏ, Số lớn, bao nhiêu số cần tạo)
Giả sử các bạn muốn tạo ra 30 số ngẩu nhiên không trùng nằm trong khoảng từ 1 đến 100, các bạn làm như sau:
- Quét chọn 30 cell tùy ý theo chiều dọc, chẳng hạn là A1:A30
- Gõ vào thanh Formula công thức =UniqueRandomNum(1,100,30)
- Bấm tổ hợp phím Ctrl + Shift + Enter
Hãy thí nghiệm với đoạn Test sau:
PHP:
Sub Test()
  Range("A1:A30").Value = UniqueRandomNum(1, 100, 30)
End Sub
--------------
Ghi chú: Dictionary Object còn làm được nhiều thứ khác nữa, chẳng hạn có thể xây dựng hàm trích lọc các phần tử duy nhất (ngẫu nhiên và duy nhất đã làm được, đương nhiên duy nhất sẽ càng dể hơn)
Nhờ bạn viết giúp mình hàm này với: Daysongaunhien (số hàng; số cột; min; max; bộ số cần tạo; kiểu sắp xếp). Trong đó: dãy số ngẫu nhiên được tạo không trùng lặp, dãy số trong mỗi hàng tăng dần từ trái qua phải; số hàng dưới luôn lớn hơn số hàng trên
 
Upvote 0
Nhờ bạn viết giúp mình hàm này với: Daysongaunhien (số hàng; số cột; min; max; bộ số cần tạo; kiểu sắp xếp). Trong đó: dãy số ngẫu nhiên được tạo không trùng lặp, dãy số trong mỗi hàng tăng dần từ trái qua phải; số hàng dưới luôn lớn hơn số hàng trên
Người mà bạn có ý nhờ viết hàm đã xa diễn đàn từ giữa tháng 12/2018 đến nay rồi!
Dù sao bạn cũng cần nêu rõ hơn:
→ Giá trị nhỏ nhất trong hàng dưới có cần lớn hơn trị cực đại của hàm trên hay không?
→ 1 bảng số liệu đã biết số dòng & số cột, cũng có nghĩa là biết được số phần tử trong bảng;
Vậy thì đề bài có thể cụ thể hóa như vầy được không:
Lấy ngẫu nhiên các con số từ 1 đến 999 lắp vô các ô trên bảng tính có 8 dòng & 12 cột
sao cho các số trong hàng hay cột đều tăng dần.

Với đề bài cụ thể này, mình cho rằng có thể có vài ba cách giải & chúc bạn thành công!

PHP:
Function BangNgauSo(Optional Rws As Byte = 8, Optional Col As Byte = 12, _
    Optional Min_ As Integer = 1, Optional Max_ As Integer = 999)
 Dim J As Integer, W As Integer, Z As Integer, Tmp As Integer
 
 If Rws > 8 Then Rws = 8
 If Col > 12 Then Col = 12
 ReDim Arr(1 To 8, 1 To 12) As String
 Randomize:             Tmp = 1
 For J = 1 To 8
    Tmp = Tmp + 1
    For Z = 1 To 12
        Tmp = 1 + Tmp + 3 * Rnd() \ 1
        Arr(J, Z) = Str(Tmp)
    Next Z
 Next J
 BangNgauSo = Arr()
End Function
 
Lần chỉnh sửa cuối:
Upvote 0
Mình có xem các bác hướng dẫn và làm file bốc thăm thi đấu loại trực tiếp cho môn Bida, anh em cần có thể lấy tham khảo, Bốc thăm ngẫu nhiên và điền tên vào Bảng thi đấu sẵn luôn nhé!
Đánh độ bi da thì người ta lắc từ túi da ra một viên bi ghi số ngẫu nhiên rối đánh dựa theo số ấy.
Số ấy người chơi giấu chặt chứ đâu có ghi bảng biếc gì.

...
Vậy thì đề bài có thể cụ thể hóa như vầy được không:
Lấy ngẫu nhiên các con số từ 1 đến 999 lắp vô các ô trên bảng tính có 8 dòng & 12 cột
sao cho các số trong hàng hay cột đều tăng dần.
...
Thuật toán:
1. chọn lấy ngẫu nhiên theo 1 trong các cách giải trên
2. chép kết quả vào một mảng (nếu không sẵn là một mảng)
3. sort mảng theo thứ tự
4. tuần tự chép kết quả vào mảng m*n. Cột trước hàng sau
 
Lần chỉnh sửa cuối:
Upvote 0
Web KT

Bài viết mới nhất

Back
Top Bottom