Chuyên đề giải đáp những thắc mắc về code VBA (2 người xem)

Liên hệ QC

Người dùng đang xem chủ đề này

maytinhvp01

Thành viên thường trực
Tham gia
27/7/13
Bài viết
390
Được thích
179
Mình muốn nhờ giải thich câu lệnh " If Ran.Cells(d, c) > max Then max = Ran.Cells(d, c) "
trong ví du:
Public Function LonNhat(Ran As Range)
Dim max As Double, v As Integer, d As Integer, c As Integer
max = Ran.Cells(1, 1)
For d = 1 To Ran.Rows.Count
For c = 1 To Ran.Columns.Count
If Ran.Cells(d, c) > max Then max = Ran.Cells(d, c)
Next c
Next d
v = Tim(max, Ran)
LonNhat = max
End Function
-------------------------------------------------------
[INFO1]Thông báo:
Vì topic này:
http://www.giaiphapexcel.com/forum/...ải-thích-các-code-đề-nghị-các-bạn-gửi-vào-đây
đã quá dài nên BQT đóng lại.
Nay tôi mở topic mới với cùng chủ đề: GIẢI THÍCH NHỮNG THẮC MẮC VỀ CODE
Các bạn nếu có nhu cầu giải thích code, vui lòng post tại đây nhé
NDU96081631

[/INFO1]
 
Chỉnh sửa lần cuối bởi điều hành viên:
Excel 3 mục ấy thì tren máy tôi luôn luôn tick rồi. Nhưng mà không hiểu sao lúc mở lên lỗi...Sau save lại...mở lên Save lại... Rồi mở lên vài lần là nó chạy bình thường ah...

ừ , bạn End code rồi thì nó cũng hết ở chế độ Protected View thì cũng hết lỗi thôi mà .
 
Upvote 0
muốn thấy lỗi ư ? để tôi giúp cho thấy
1/check như hình dưới đây

c73afb1281f4c3f1b220cd78a450121a.png

2/bấm nút tải file ở trên vài lần
3/mở cái file cuối cùng mới tải xuống
4/bấm nút Enable Editing

7a064d41a781d48e79eaf04c5246214a.png


thử xem =))
Có cách nào gửi file cho máy khác mà không bị lỗi vậy không anh
em cảm ơn anh ạ
 
Upvote 0
Xin chào các bạn trong diễn đàn,
Mình có đoạn code sau xin các cao thủ giải thích hộ
Private Sub SetText(Text as String, XPos As integer, YPos as integer)
Session.autECLPS.SetCursorPos XPos,YPos
Session.autECLPS.SendKeys Finestring(text)
End Sub

Đặc biệt "autoECLPS" và "autoECLOIA" là gì ạ?



Set ConnectionList= CreateObject("PCOMM.autECLConnList")
Set Session= CreateObject("PCOMM.autECLSession")
Set OperationInformationArea= CreateObject("PCOMM.autECLOIA")
 
Upvote 0
Nhờ AE hổ trợ! Mình có đoạn code sau, mình muốn copy từ Workbook 1 sheet Addition sang workbook 2 ở sheet Addition nhưng vẫn giữ lại dữ liệu cũ ở workbook 2 ở sheet Addition. Mình nó paste qua nhưng bị mất dữ liệu trước đó. Mới học VBA nên còn dốt quá.

Cám ơn cả nhà!

Sub Macro1thunghiem()
'
' Macro1thunghiem Macro
'


'
Rows("A3:AE20").Select
Selection.Copy
ChDir "D:\BAO CAO"
Workbooks.Open Filename:="D:\BAO CAO\BAO CAO TUAN.xlsx"
Range("A4:AE18").Select
Selection.PasteSpecial Paste:=xlPasteValues, Operation:=xlNone, SkipBlanks _
:=False, Transpose:=False
Application.CutCopyMode = False
ActiveWorkbook.Save
ActiveWindow.Close
End Sub
 
Upvote 0
Nên đưa file giả lập lên diễn đàn, bạn à!
 
Upvote 0
Nên đưa file giả lập lên diễn đàn, bạn à!

Cám ơn Bạn: mình đã làm được rồi. Mình cho nó chung 1 Workbook luôn. Nhưng phát sinh vấn đề là các dòng ko có dữ liệu nó cung copy luôn.
Nhờ bạn kiểm tra giúp nhé!

Public Sub Copyprofile()
Dim dong As Long
dong = Sheet8.Range("E" & (Sheet8.Range("E65000").End(xlUp).Row)).Row - 1
Sheet13.Range("A" & (Sheet13.Range("E65000").End(3).Row + 1)).Resize(dong, 25).Value = Sheet8.Range("B2").Resize(dong, 25).Value
MsgBox "XUAT XONG"
End Sub
 
Upvote 0
. . Mình đã làm được rồi, cho nó chung 1 Workbook luôn. Nhưng phát sinh vấn đề là các dòng ko có dữ liệu nó cung copy luôn.
Nhờ bạn kiểm tra giúp nhé!

Public Sub Copyprofile()
Dim dong As Long
dong = Sheet8.Range("E" & (Sheet8.Range("E65000").End(xlUp).Row)).Row - 1
Sheet13.Range("A" & (Sheet13.Range("E65000").End(3).Row + 1)).Resize(dong, 25).Value = Sheet8.Range("B2").Resize(dong, 25).Value
MsgBox "XUAT XONG"
End Sub

Thì bạn thay vì xài .End(3) thì xài .End(xlDown) để copy từng đoạn có dữ liệu vậy; Thử nghiên cứu tiếp đi, đến khi mõi mết thì đưa file lên!

Chúc thành công!
 
Upvote 0
HIHI! Bác GIÚP GIÙM NHÉ. CÁM ƠN BÁC!
PHP:
Option Explicit
Public Sub CopyProfile()
Dim Dong As Long, Cot As Byte
Dim Cls As Range
Sheet8.Select
Cot = [b1].CurrentRegion.Columns.Count
Dong = Range("E65000").End(xlUp).Row
For Each Cls In [E2].Resize(Dong)
    If Cls.Value <> "" Then
        Cells(Cls.Row, "B").Resize(, Cot).Copy Destination:=Sheet13.[B65500].End(xlUp).Offset(1)
    End If
Next Cls
MsgBox "XUAT XONG", , "GPE.COM"
End Sub
 
Upvote 0
Bạn cho hỏi là sao phải truyền tham số vậy bạn, và phải tách ra 2 sub ? Điều này có tác dụng gì???

Và tại sao không dùng trong 1 sub luôn cho gon...& không cần truyền tham số nhưng vẫn xác định được dòng cột nào muốn tách, muốn ghi dữ liệu...

=> Gôm vào 1 sub & không cần truyền tham số như bạn thì tốc độ sẽ cải thiện & tức thời hơn rất nhiều (nhanh hơn).

=========================
Giờ nâng độ khó lên tí:

Cũng với dữ liệu trên, chỉ cần 1 Mảng nguồn & 1 mảng đích, không hạn chế vòng lặp (nhưng làm sao cho nó ít nhất) & code để ra kết quả như trên sheet Database của bạn...

Cùng tham gia nhé!

P/s: Vì thấy bài này cho cái dữ liệu thấy hay hay...@$@!^%@$@!^%@$@!^%
Trong lập trình nếu muốn tối ưu cách viết và quản lý thì phải biết chia nhỏ các vấn đề ra để giải quyết, đó là cách tốt nhất. bạn có thể tham khảo trên các diễn đàn để biết. và chia nhỏ các vấn đề để trị có thể được gọi là đỉnh cao trong công việc lập trình

ví dụ như bạn muốn làm 10 cái bông hồng giống nhau nhưng khác nhau về màu sắc thì bạn làm như thế nào?
cách 1 cố làm ra 10 bông giống nhau từng cái riêng rẻ
cách 2 là tạo ra 1 cái khuôn, muốn màu nào thì đổ màu đó ra

nhận xét
cách 1 là cách dễ sai sót nhất. bạn có dám chắc là 10 cái bông đó giống y chang không? và có chắc là đã kiểm soát được không?
cách 2 nếu bị sai thì sẽ sai hàng loạt vì vậy dễ phát hiện và chắc chắn kiểm soát được 100%

cách 1. có cùng 1 công việc mà lập đi lập lại nhiều lần tạo ra nhiều bông
cách 2. chỉ cần đổ nguyên liệu vào khuôn thì ok ngay
nếu tạo 1 bông thì có thể cách 1 nhanh hơn
nếu càng nhiều bông thì cách 1 chuối hơn cách 2 nhiều
 
Upvote 0
PHP:
option explicit
public sub copyprofile()
dim dong as long, cot as byte
dim cls as range
sheet8.select
cot = [b1].currentregion.columns.count
dong = range("e65000").end(xlup).row
for each cls in [e2].resize(dong)
    if cls.value <> "" then
        cells(cls.row, "b").resize(, cot).copy destination:=sheet13.[b65500].end(xlup).offset(1)
    end if
next cls
msgbox "xuat xong", , "gpe.com"
end sub

sao nó ko copy value mà nó copy cả công thức vậy bạn? Cách chạy thì đúng rồi
 
Upvote 0
Các anh chị cho em hỏi:

Bây giờ em có 1 file excel, 1 sheet bao gồm dữ liệu gồm danh sách các mã hàng..., bây giờ em lọc một phần dữ liệu rồi em muốn khi gửi cho 1 người thì người đấy không thể sử dụng lọc để show dữ liệu khác ra được, nhưng vẫn có thể nhập được dữ liệu ( có nghĩa là khóa chức năng lọc lại, không cho sử dụng lọc).

Có cách nào hay phải dùng code, mong các anh chị giúp đỡ!
 
Upvote 0
Các bác cho e hỏi chút ạ: E thấy m.n hay khai báo:
Dim i as Long
Dim j as Long
Dim g as Long
...
Vậy bây giờ khai báo thành Dim i,j,g as Long có ảnh hưởng gì ko ạ
 
Upvote 0
Các bác cho e hỏi chút ạ: E thấy m.n hay khai báo:
Dim i as Long
Dim j as Long
Dim g as Long
...
Vậy bây giờ khai báo thành Dim i,j,g as Long có ảnh hưởng gì ko ạ

Ví dụ khi ta chỉ khai báo là Dim a ( khai báo kiểu mập mờ ) thì VBA sẽ mặc định kiểu dữ liệu của biến a là Variant

Suy ra:

Nếu bạn khai báo như ở trên thì chỉ có g được khai báo với kiểu dữ liệu là Long thôi còn i, j mặc định sẽ là Variant
 
Upvote 0
Ví dụ khi ta chỉ khai báo là Dim a ( khai báo kiểu mập mờ ) thì VBA sẽ mặc định kiểu dữ liệu của biến a là Variant

Suy ra:

Nếu bạn khai báo như ở trên thì chỉ có g được khai báo với kiểu dữ liệu là Long thôi còn i, j mặc định sẽ là Variant
E hiểu roài ạ, thank bác --=0
 
Upvote 0
Các bác cho em hỏi chút ạ, E có yêu cầu như trong File về phương thức Find. E cảm ơn ạ
 

File đính kèm

Upvote 0
Các bác cho em hỏi chút ạ, E có yêu cầu như trong File về phương thức Find. E cảm ơn ạ

Fương thức này không thể áp dụng để tìm 1 tháng cụ thể nào trong cột dữ liệu chứa ngày tháng kiểu DD/mm/yyyy hay MM/dd/yyyy

Hơn nữa, bạn cần lưu í 1 điều rằng khi cần tìm dữ liệu kiểu ngày tháng, ta cần định dạng toàn bộ vùng cần tìn về dạng 'MM/DD/YYYY'; Xài các dạng khác như Dd/MM/yyyy hay MM/DD/yy đều tiềm ẩn nguy cơ sai lệnh khôn lường.
 
Upvote 0
Fương thức này không thể áp dụng để tìm 1 tháng cụ thể nào trong cột dữ liệu chứa ngày tháng kiểu DD/mm/yyyy hay MM/dd/yyyy

Hơn nữa, bạn cần lưu í 1 điều rằng khi cần tìm dữ liệu kiểu ngày tháng, ta cần định dạng toàn bộ vùng cần tìn về dạng 'MM/DD/YYYY'; Xài các dạng khác như Dd/MM/yyyy hay MM/DD/yy đều tiềm ẩn nguy cơ sai lệnh khôn lường.
Vậy chỉ có giải pháp thêm 1 cột phụ bên cạnh, và dùng hàm Month của Excel thôi à a ơi :(
 
Upvote 0
Code này tạo 1 dãy 4, hoặc 5 số và chuỗi ngẫu nhiên, nhưng mình chưa hiểu cách hoạt động của nó như thế nào, xin các bác chỉ giáo
Mã:
Function GetRandName() As String
  GetRandName = Mid(CreateObject("Scripting.FileSystemObject").GetTempName, 4, 5)
End Function
 
Upvote 0
Vậy chỉ có giải pháp thêm 1 cột phụ bên cạnh, và dùng hàm Month của Excel thôi à a ơi :(

Nếu vẫn muốn xài fương thức FOND() thì chịu khó tạo vòng lặp duyệt tìm tấn tần tật các ngày trong tháng đó có trong CSDL; Như kiểu:

Set Rng = Range("B2: B999")
Rng.NumFormat="MM/DD/yyyy"
For J= 1 To 31
Dat = Format(DateSerial(Nam, Thang,J),"MM/DD/yyyy")
Set sRng=Rng.Find(Dat,,XlValues,Xlwhole)

Next J
 
Upvote 0
Code này tạo 1 dãy 4, hoặc 5 số và chuỗi ngẫu nhiên, nhưng mình chưa hiểu cách hoạt động của nó như thế nào, xin các bác chỉ giáo
Mã:
Function GetRandName() As String
  GetRandName = Mid(CreateObject("Scripting.FileSystemObject").GetTempName, 4, 5)
End Function
GetTempName dùng để tạo chuỗi ký tự để đặt tên cho file tạm.
Bạn vào tools-reference đánh dấu vào Microsoft Scripting Runtime. Copy code vào module:
Mã:
Sub a()
Set f = New FileSystemObject
Do
tmp = f.GetTempName
Loop
End Sub
Bấm F8 nhiều lần, quan sát biến tmp trong cửa sổ Local. Bạn sẽ thấy tmp có dạng rad?????.tmp, trong đó ????? là 5 ký tự ngẫu nhiên. Hàm mid(tmp,4,5) lấy ra 5 ký tự ngẫu nhiên đó.
 
Upvote 0
GetTempName dùng để tạo chuỗi ký tự để đặt tên cho file tạm.
Bạn vào tools-reference đánh dấu vào Microsoft Scripting Runtime. Copy code vào module:
Mã:
Sub a()
Set f = New FileSystemObject
Do
tmp = f.GetTempName
Loop
End Sub
Bấm F8 nhiều lần, quan sát biến tmp trong cửa sổ Local. Bạn sẽ thấy tmp có dạng rad?????.tmp, trong đó ????? là 5 ký tự ngẫu nhiên. Hàm mid(tmp,4,5) lấy ra 5 ký tự ngẫu nhiên đó.
Cám ơn bạn, giờ mình đã hiểu
 
Upvote 0
Mọi người cho em xin code thay cho lệnh này excel với ạ? Em chạy lệnh như này cho nhiều ô nên file bị nặng quá :( Mấy hôm nay chập chững đọc tài liệu VBA mà càng đọc lại càng rối trong khi việc thì đang cần gấp

=IF(ISNA(INDEX(DATA,MATCH(1,(C.I<=$A$2)*(C.O>=$A$2)*(No.Room=A4)*(Don_gia>0)*(Guest=1),0),12)),"",INDEX(DATA,MATCH(1,(C.I<=$A$2)*(C.O>=$A$2)*(No.Room=A4)*(Don_gia>0)*(Guest=1),0),12))

Các dữ liệu: DATA; C.I ; C.O; No.Room ; Don_gia; Guest là vùng Define Name.

Em cám ơn mọi người nhiều ạ!
 
Upvote 0
Mọi người cho hỏi:
Em có file gồm nhiều sheets có liên kết với nhau bằng các công thức, tên và code trong mỗi sheets. Code trong mỗi sheets (sheets ;2;3;4;5) được viết để thay đổi khi dữ liệu ở sheet 1 thay đổi.
Khi thay đổi dữ liệu sheets 1 mà muốn code ở sheets 2;3;4;5 chạy nó bắt em phải click vào sheets đó đã. Em muốn in đồng loạt từ sheets 1 đến sheets 5 nhưng chỉ cần thay đổi dữ liệu ở sheet1 thôi và bấm in. Làm cách nào để code tự chạy ở các sheets khác mà ko cần click chọn hiển thị sheets đó.
Xin cảm ơn!!!
 
Upvote 0
Mọi người cho hỏi:
Em có file gồm nhiều sheets có liên kết với nhau bằng các công thức, tên và code trong mỗi sheets. Code trong mỗi sheets (sheets ;2;3;4;5) được viết để thay đổi khi dữ liệu ở sheet 1 thay đổi.
Khi thay đổi dữ liệu sheets 1 mà muốn code ở sheets 2;3;4;5 chạy nó bắt em phải click vào sheets đó đã. Em muốn in đồng loạt từ sheets 1 đến sheets 5 nhưng chỉ cần thay đổi dữ liệu ở sheet1 thôi và bấm in. Làm cách nào để code tự chạy ở các sheets khác mà ko cần click chọn hiển thị sheets đó.
Xin cảm ơn!!!
Úp file bạn muốn thay đổi các sheet đó lên đây
 
Upvote 0
Ko được anh ơi... nó vẫn vậy ko khác điều gì. vui nó chạy mà buồn nó ko anh ơi.
 
Lần chỉnh sửa cuối:
Upvote 0
Câu lệnh thay thế cho toán tử so sánh trong VBA

Chao mọi người. Em có vấn đề này cần được sự trợ giúp ạ.Em có đoạn Code sau:
Mã:
Sub hoi()
  bl As Boolean
  bl = 3 < 4
  MsgBox bl
End Sub


Tuy nhiên giờ em mốn viết khác đi như sau:

Mã:
Sub hoi()
  Dim ss As String, bl As Boolean
  ss = "<"
[COLOR=#ff0000][B]  bl = 3 & ss & 4[/B][/COLOR]
  MsgBox bl
End Sub

Nhờ mọi người viết giúp em câu lệnh màu đỏ thế nào để VBA hiểu được ạ
 
Upvote 0
Chao mọi người. Em có vấn đề này cần được sự trợ giúp ạ.Em có đoạn Code sau:
Mã:
Sub hoi()
  bl As Boolean
  bl = 3 < 4
  MsgBox bl
End Sub


Tuy nhiên giờ em mốn viết khác đi như sau:

Mã:
Sub hoi()
  Dim ss As String, bl As Boolean
  ss = "<"
[COLOR=#ff0000][B]  bl = 3 & ss & 4[/B][/COLOR]
  MsgBox bl
End Sub

Nhờ mọi người viết giúp em câu lệnh màu đỏ thế nào để VBA hiểu được ạ
Hãy thử khai báo biến với bl as string xem sao nhé. Mà muốn trả về kết quả là True hay sao?
 
Lần chỉnh sửa cuối:
Upvote 0
Sub hoi()
Dim ss As String, bl As Boolean
ss = ">"
bl = Evaluate(3 & ss & 4)
MsgBox bl
End Sub
 
Upvote 0
Các bạn giúp mình fix lỗi trong đoạn code bên dưới với. Lần đầu chạy thì Chart tự động vẽ được, nhưng sau đó thì ko đươc và báo lỗi " Method or datamember not found", lỗi ở phần ".SetSourceData"
Các bạn giúp mình với nhé:

Sub ChartSheetExample()


Dim ChartSheet2 As Chart


Set ChartSheet2 = Charts.Add


With ChartSheet2
.SetSourceData Source:=Sheets("Sheet2").Range("B1:B11")
.ChartType = xlColumnClustered
.HasTitle = True
.ChartTitle.Text = "Chart Sheet Example"
.Axes(xlCategory, xlPrimary).HasTitle = True
.Axes(xlCategory, xlPrimary).AxisTitle.Characters.Text = Range("A1")
.Axes(xlValue, xlPrimary).HasTitle = True
.Axes(xlValue, xlPrimary).AxisTitle.Characters.Text = Range("B1")

End With
End Sub
 
Upvote 0
nhờ mọi người giúp trường hợp sau:
từ C5:C12 tôi có một số chuổi text như sau:
se,qw,rty,se,ce,aw,#N/A
và có đoạn code sau:
Mã:
Sub taisao()
Dim arr As Variant
arr = [c5:c12].Value

For i = 1 To UBound(arr)
    If arr(i, 1) = "ce" Then MsgBox "ce"
Next

End Sub
nó chạy tới chổ #N/A thì báo lổi
vậy phải làm sao?
cám ơn
 
Upvote 0
nhờ mọi người giúp trường hợp sau:
từ C5:C12 tôi có một số chuổi text như sau:
se,qw,rty,se,ce,aw,#N/A
và có đoạn code sau:
Mã:
Sub taisao()
Dim arr As Variant
arr = [c5:c12].Value

For i = 1 To UBound(arr)
    If arr(i, 1) = "ce" Then MsgBox "ce"
Next

End Sub
nó chạy tới chổ #N/A thì báo lổi
vậy phải làm sao?
cám ơn

sao em bỏ zô máy nhà chạy có tới dòng For i = 1 To UBound(arr)
là lỗi luôn rồi anh ơi , chưa tới được vòng NA . hu hu !$@!!!$@!!
 
Upvote 0
nhờ mọi người giúp trường hợp sau:
từ C5:C12 tôi có một số chuổi text như sau:
se,qw,rty,se,ce,aw,#N/A
và có đoạn code sau:
Mã:
Sub taisao()
Dim arr As Variant
arr = [c5:c12].Value

For i = 1 To UBound(arr)
    If arr(i, 1) = "ce" Then MsgBox "ce"
Next

End Sub
nó chạy tới chổ #N/A thì báo lổi
vậy phải làm sao?
cám ơn
Đưa vào mảng thì nó không chấp nhận dữ liệu lỗi
 
Lần chỉnh sửa cuối:
Upvote 0
Chào cả nhà!
Mình có đoan code tìm kiếm mã quản lý. Nếu tìm thấy mã đó ở dòng nào thì nó sẽ điền đúng dữ liệu bổ sung vào dòng đó tương ứng.
Code của mình không hiểu sao lỗi chỗ nào mà không cập nhật được
Mã:
Private Sub CommandButton1_Click()
    Dim vung As Range, MyR As Range
    Set vung = S2.Range("A5:A65000")
    Set MyR = vung.Find(frmCapNhatKH.TextBox1.Value, , xlValues, xlWhole) ' Tim ma quan ly o cot A
    If frmCapNhatKH.ComboBox1.Value = "" Then
        MsgBox ("Ma quan ly khong duoc de trong!"), vbCritical, "ABC"
        frmCapNhatKH.ComboBox1.SetFocus
    Else
        If MyR Is Nothing Then
            With MyR 'Em khong hieu doan nay loi sao nua?
                'Cap nhat vao cot Q
                .Offset(, 16).Value = frmCapNhatKH.TextBox1.Value 'Bao loi dong nay
                'Cap nhat vao cot R
                .Offset(, 17).Value = frmCapNhatKH.TextBox2.Value
                'Cap nhat vao cot S
                .Offset(, 18).Value = frmCapNhatKH.TextBox3.Value
                'Cap nhat vao cot T
                .Offset(, 19).Value = frmCapNhatKH.TextBox4.Value
            End With
            With frmCapNhatKH
                .ComboBox1.SetFocus
                .ComboBox1.Value = ""
                .TextBox1.Value = ""
                .TextBox2.Value = ""
                .TextBox3.Value = ""
                .TextBox4.Value = ""
            End With
        Else
            MsgBox ("Ma quan ly nay khong ton tai!"), vbCritical, "ABC"
            frmCapNhatKH.ComboBox1.SetFocus
        End If
    End If
    Set MyR = Nothing
    Set vung = Nothing
End Sub
Vậy nhờ mọi người nhìn cho mình xem đoạn code trên bất hợp lý ở chỗ nào??
Cám ơn mọi người nhiều!
 

File đính kèm

Lần chỉnh sửa cuối:
Upvote 0
Theo mình mơ màng hiểu (vì không có file để cụ thể thêm) thì bạn nên sửa, chỉnh 2 nơi:

1./ Trước khi bắt chương trình đi tìm cái gì đó đang có trong frmCapNhatKH.TextBox1.Value, bạn fải xem cái này đang có dữ liệu hay chưa;
Nếu đi tìm "" hay " " là bạn bắt chương trình đi tìm cái vu vơ rồi còn gì?

2./ Câu lệnh này đúng ngữ fáp & chính tả: "If MyR Is Nothing Then "
Nhưng sai về cách ra lệnh;
Cũng giống như bạn ra lệnh cho thằng con:

Mày ra chợ tìm cô bán rau muống bữa trước; Nếu không thấy thì đưa cô ta về đây!
 
Upvote 0
Theo mình mơ màng hiểu (vì không có file để cụ thể thêm) thì bạn nên sửa, chỉnh 2 nơi:

1./ Trước khi bắt chương trình đi tìm cái gì đó đang có trong frmCapNhatKH.TextBox1.Value, bạn fải xem cái này đang có dữ liệu hay chưa;
Nếu đi tìm "" hay " " là bạn bắt chương trình đi tìm cái vu vơ rồi còn gì?

2./ Câu lệnh này đúng ngữ fáp & chính tả: "If MyR Is Nothing Then "
Nhưng sai về cách ra lệnh;
Cũng giống như bạn ra lệnh cho thằng con:

Mày ra chợ tìm cô bán rau muống bữa trước; Nếu không thấy thì đưa cô ta về đây!
Em đã sửa như vầy vẫn không được ạ. Nhờ anh chỉ giao thêm ạ!
Mã:
Private Sub CommandButton1_Click()
    Dim vung As Range, MyR As Range
    If frmCapNhatKH.ComboBox1.Value = "" Then
        MsgBox ("Ma quan ly khong duoc de trong!"), vbCritical, "ABC"
        frmCapNhatKH.ComboBox1.SetFocus
    Else
    Set vung = S2.Range("A5:A65000")
    Set MyR = vung.Find(frmCapNhatKH.TextBox1.Value, , xlValues, xlWhole) ' Tim ma quan ly o cot A
        If MyR Is Nothing Then
            With MyR 'Em khong hieu doan nay loi sao nua?
                'Cap nhat vao cot Q
                .Offset(, 16).Value = frmCapNhatKH.TextBox1.Value 'Bao loi dong nay
                'Cap nhat vao cot R
                .Offset(, 17).Value = frmCapNhatKH.TextBox2.Value
                'Cap nhat vao cot S
                .Offset(, 18).Value = frmCapNhatKH.TextBox3.Value
                'Cap nhat vao cot T
                .Offset(, 19).Value = frmCapNhatKH.TextBox4.Value
            End With
            With frmCapNhatKH
                .ComboBox1.SetFocus
                .ComboBox1.Value = ""
                .TextBox1.Value = ""
                .TextBox2.Value = ""
                .TextBox3.Value = ""
                .TextBox4.Value = ""
            End With
        Else
            MsgBox ("Ma quan ly nay khong ton tai!"), vbCritical, "ABC"
            frmCapNhatKH.ComboBox1.SetFocus
        End If
    End If
    Set MyR = Nothing
    Set vung = Nothing
End Sub
 
Upvote 0
Bạn mới sửa điều (1) thôi!

Còn điều (2) nữa!

Mày ra chợ tìm cô bán rau muống bữa trước; Nếu không thấy thì đưa cô ta về đây!
 
Upvote 0
Không được ạ! Em làm rùi anh ơi.....! Anh thử file của em đính kèm ở #697 thử xem.
Chẳng lẽ hết cách rùi sao ạ!
Ngoài việc sửa chỗ đó ra thì còn phải sửa đối tượng cần tìm ở câu lệnh Set MyR = vung.Find(..., đối tượng cần tìm là ComboBox1 chứ không phải là TextBox1
 
Upvote 0
Đúng là sai rất cơ bản mà không phát hiện ra ạ!
Để tránh sai như vậy, mình thường chú tâm trong việc gán tên cho các đối tượng Control, như

TxtHoTen; TxtNgaySinh, . . . cho các TextBox
CbBDonVi, CbBLop, CbBNganh,. . . cho các ComboBox
& CmdLuu, CmdXoa, . . . . cho các nút lệnh

Với cả các nhãn kèm theo cũng vậy, như LblNSinh, LblDonVi,. . . . .
 
Upvote 0
giải thích đoạn code này dùm em.

Option Explicit


Public Sub GPE()
Dim sArr(), dArr(1 To 1, 1 To 16), I As Long, J As Long, K As Long
sArr = Range("C3:I19").Value
For J = 1 To 5 Step 4
For I = 1 To 17 Step 2
If sArr(I, J) <> Empty Then
K = K + 1
dArr(1, K) = sArr(I, J + 2)
End If
Next I
Next J
For I = 3 To 17 Step 2
Range("E" & I).ClearContents
If I < 8 Then Range("I" & I).ClearContents
Next I
For I = 11 To 19 Step 2
Range("I" & I).ClearContents
Next I
Range("E3").Select
Sheet2.Range("A64").End(xlUp).Offset(1).Resize(, 16) = dArr
End Sub
 
Upvote 0
E dùng InputBox:
Dim m as String
m = Application.InputBox(UNC("LÝ do in l¹i"), Type:=2) '(m là Text)

E muốn khi chọn Cancel thì sẽ nhảy đến nhãn Thoát chứ không phải chạy tiếp tục lệnh sau đó, thì dùng If như thế nào vậy ạ
 
Upvote 0
E dùng InputBox:
Dim m as String
m = Application.InputBox(UNC("LÝ do in l¹i"), Type:=2) '(m là Text)

E muốn khi chọn Cancel thì sẽ nhảy đến nhãn Thoát chứ không phải chạy tiếp tục lệnh sau đó, thì dùng If như thế nào vậy ạ
PHP:
m = Application.InputBox(UNC("LÝ do in l¹i"), Type:=2)           '(m là Text)
If m = "False" Then GoTo Thoat
Tuy nhiên, nếu bạn nhập vào InputBox chữ 'False' thì cũng nhảy đến nhãn Thoat. Muốn khắc phục thì phải sửa lại kiểu của biến m.
 
Upvote 0
PHP:
m = Application.InputBox(UNC("LÝ do in l¹i"), Type:=2)           '(m là Text)
If m = "False" Then GoTo Thoat
Tuy nhiên, nếu bạn nhập vào InputBox chữ 'False' thì cũng nhảy đến nhãn Thoat. Muốn khắc phục thì phải sửa lại kiểu của biến m.
E làm được rùi, thank bác ạ
 
Lần chỉnh sửa cuối:
Upvote 0
Nhờ các cao thủ thông não giúp e với ạ. trình độ e còn xanh quá nên ko hiểu cái này là như thế nào cả... cảm ơn các bác


Option Explicit
Type BarElement
Mark As String
Diameter As Byte
Quantity As Long
No As Long
Length As Double
End Type
Type BarDetail
Dia As Byte
MaxNum As Byte
TotalNum As Integer
CurrentNum As Integer
Mark As String
Length As Double
MinLength As Double
End Type
Public Type SumLength
Value As Double
Note As String
End Type
Public maxLength As Double
Public maxResult As Double
Public maxString As String
Public tmpBar As Integer
Public tmpNum As Byte
Public barIndex As Long
Public cutIndex As Long
Public lapLength As Double
Public devLength As Double
Public cutOption As Byte
Public constPI As Double
Public isDemo As Boolean

Public Sub CutBarMainControl()
Call GetInitialData
'isDemo = True
'If InStr(Application.Caption, "REGISTERED") <> 0 Then isDemo = True
'isDemo = True
'If isDemo = True Then
' If MsgBox("Not registered vesion. Run DEMO program?", vbInformation + vbYesNoCancel, "Before running") = vbYes Then
' 'Call mdlCreateRandom.CreateRandom
' Call SortInputData
' Else
' If MsgBox("Not registered vesion. Run DEMO program?", vbInformation + vbYesNoCancel, "Before running") = vbNo Then
' Load frmActivate
' frmActivate.Show
' End If
' End If
' Else
Call SortInputData
'End If
End Sub

Private Sub GetInitialData()
maxLength = Sheets("Input").Cells(2, 6)
devLength = Sheets("Input").Cells(3, 6)
lapLength = Sheets("Input").Cells(4, 6)
cutOption = Sheets("Input").Cells(5, 6)
cutIndex = 0
constPI = Application.WorksheetFunction.Pi()
'Clear old data in sheet Result
Sheets("Result").Activate
Cells(1, 5) = 0
Range("A4:K65536").Clear 'Number of row in a sheet is 65536
End Sub

Private Sub SortInputData()
ActiveWorkbook.Application.StatusBar = "Analyzing and sorting data..."
Dim arrDiameter(1 To 15) As Byte
Dim arrWeight(1 To 15) As Double
Dim arrBar(1 To 15, 1 To 500) As BarElement
Dim arrNum(1 To 15) As Long
Dim curBarDia As Byte
Dim curBarLength As Double
Dim curBarMark As String
Dim curBarQuantity As Long
Dim curBarNo As Long
Dim i&, j&, l&
Dim k As Byte
Dim tmpMu As Integer
'Initilize list of support Diameters
For i = 1 To 15
arrDiameter(i) = Sheets("Input").Cells(2, i + 8)
Next i
For i = 1 To 15
arrNum(i) = 0
arrWeight(i) = 0
Next i
'Set initial Cell Index
i = 9
Sheets("Input").Activate
Do While Trim(Cells(i, 4)) <> "" 'Cot duong kinh khac 0
Cells(i, 2) = i - 8
curBarNo = i - 8
curBarMark = Trim(Cells(i, 3))
curBarDia = Trim(Cells(i, 4))
curBarQuantity = Trim(Cells(i, 5))
curBarLength = Trim(Cells(i, 6))
For j = 1 To 15
If arrDiameter(j) = curBarDia Then
arrNum(j) = arrNum(j) + 1
arrBar(j, arrNum(j)).No = curBarNo
arrBar(j, arrNum(j)).Mark = curBarMark
arrBar(j, arrNum(j)).Diameter = curBarDia
arrBar(j, arrNum(j)).Quantity = curBarQuantity
arrBar(j, arrNum(j)).Length = curBarLength
arrWeight(j) = arrWeight(j) + (((curBarDia ^ 2 * constPI / 4) * curBarLength) * 7850 * curBarQuantity) / 1000000
Exit For
End If
Next j
i = i + 1
Loop
Range("B9:G" & i - 1).Select
Call FormatInputTable
Range("B9:C" & i - 1).Select
Selection.HorizontalAlignment = xlCenter

'Dien DK va khoi luong vao Remain
For i = 1 To 15
Sheets("Remain").Cells(i + 3, 7) = arrDiameter(i)
Sheets("Remain").Cells(i + 3, 8) = arrWeight(i)
Next i
Sheets("Result").Activate
For j = 1 To 15
If arrNum(j) > 0 Then
ActiveWorkbook.Application.StatusBar = "Filtering data to Diameter: " & arrDiameter(j)
'Get current row index
barIndex = Cells(1, 5)
'Transfer data to ActiveSheet
l = 0
For i = 1 To arrNum(j)
l = l + 1
If arrBar(j, i).Length > maxLength Then
tmpMu = Int(arrBar(j, i).Length / (maxLength - lapLength * arrDiameter(j) / 1000))
Cells(barIndex + l + 3, 1) = arrBar(j, i).No
Cells(barIndex + l + 3, 2) = arrBar(j, i).Diameter
Cells(barIndex + l + 3, 3) = arrBar(j, i).Mark
Cells(barIndex + l + 3, 4) = arrBar(j, i).Quantity * tmpMu
Cells(barIndex + l + 3, 5) = maxLength
l = l + 1
arrBar(j, i).Length = arrBar(j, i).Length - tmpMu * (maxLength - lapLength * arrDiameter(j) / 1000)
End If
Cells(barIndex + l + 3, 1) = arrBar(j, i).No
Cells(barIndex + l + 3, 2) = arrBar(j, i).Diameter
Cells(barIndex + l + 3, 3) = arrBar(j, i).Mark
Cells(barIndex + l + 3, 4) = arrBar(j, i).Quantity
Cells(barIndex + l + 3, 5) = arrBar(j, i).Length
Next i
Cells(1, 5) = Cells(1, 5) + l
'Sort data
Range("A" & barIndex + 3 & ":E" & barIndex + l + 3).Select
Selection.Sort key1:=Range("E" & barIndex + 3), Order1:=xlDescending, Header:=xlGuess, OrderCustom:=1, MatchCase:=False, Orientation:=xlTopToBottom
ActiveWorkbook.Application.StatusBar = "Opimizing cutting bar for Diameter: " & arrDiameter(j)
'Format data from column A to D
Range("A" & barIndex + 4 & ":D" & barIndex + l + 3).Select
Selection.NumberFormat = "0"
Selection.HorizontalAlignment = xlCenter
'Format data from column A to E
Range("E" & barIndex + 4 & ":E" & barIndex + l + 3).Select
Selection.NumberFormat = "0.000"
'Format cell borders
Range("A" & barIndex + 4 & ":E" & barIndex + l + 3).Select
Call FormatInputTable
Call CutbarAnalyze(arrDiameter(j))
Range("A" & barIndex + 3 & ":E" & barIndex + l + 3).Select
Selection.Sort key1:=Range("A" & barIndex + 3), Order1:=xlAscending, Header:=xlGuess, OrderCustom:=1, MatchCase:=False, Orientation:=xlTopToBottom
End If
Next j
ActiveWorkbook.Application.StatusBar = "Controlling remain steel for the next usage"
Cells(1, 9) = "Optimization finished!"
Call ControlRemainSteel
ActiveWorkbook.Application.StatusBar = "Ready"
End Sub

Private Sub ClearCurrentSheet(intCount As Long)
Dim i&, j&
Cells(1, 6) = ""
i = 4
Do While Trim(Cells(i, 5) <> "")
i = i + 1
Loop
j = i
If intCount >= j Then j = intCount
Rows("4:" & j).Select
Selection.Delete Shift:=xlUp

End Sub

Private Sub CutbarAnalyze(curBarDiameter)
Dim i&, j&, k&, l&, m&, iPos&
Dim sCnt&, iCnt&
Dim MaxBar As Long
Dim iniLength As Double
Dim useLength As Double
Dim resLength As Double
Dim maxNumUse As Long
Dim strKey As String
Dim strAnl As String
Dim curMaxNum As Byte
Dim curBar() As BarDetail
Dim curNum() As Integer
Dim curFac() As Integer
Dim curSumLength(1 To 500) As SumLength
Dim curSumMin(1 To 500) As SumLength
Dim curCOM(1 To 500) As SumLength
Dim strNum(1 To 500) As String
Dim strDisplay As String
'Get MaxBar form current sheet
MaxBar = Cells(1, 5)
'ReDefined array
If MaxBar > 0 Then
ReDim curBar(1 To MaxBar) As BarDetail
ReDim curNum(1 To MaxBar) As Integer
ReDim curFac(1 To MaxBar) As Integer
iniLength = 0
useLength = 0
For i = barIndex + 1 To MaxBar
curBar(i).Mark = Cells(i + 3, 3)
curBar(i).TotalNum = Cells(i + 3, 4)
curBar(i).CurrentNum = Cells(i + 3, 4)
curBar(i).Length = Cells(i + 3, 5)
iniLength = iniLength + curBar(i).Length * curBar(i).TotalNum
curBar(i).MinLength = curBar(i).Length * (1 - devLength)
curBar(i).MaxNum = Fix(maxLength / curBar(i).MinLength)
Next i
'Cells index to put result
i = 1
iPos = 4
Do While i <= MaxBar
Do While curBar(i).CurrentNum > 0
sCnt = 0
For j = 1 To minValue(curBar(i).MaxNum, curBar(i).CurrentNum)
sCnt = sCnt + 1
curSumLength(sCnt).Value = j * curBar(i).Length
curSumMin(sCnt).Value = j * curBar(i).MinLength
curSumLength(sCnt).Note = "Bar" & i & "Num" & j
Next j
k = i + 1
Do While k <= MaxBar
If curBar(k).CurrentNum > 0 Then
m = 0
For iCnt = 1 To sCnt
For l = 1 To minValue(curBar(k).MaxNum, curBar(k).CurrentNum)
'curSumLength(iCnt).Value + l * curBar(k).Length <= maxlength Or
If curSumMin(iCnt).Value + l * curBar(k).MinLength <= maxLength Then
m = m + 1
curSumLength(sCnt + m).Value = curSumLength(iCnt).Value + l * curBar(k).Length
curSumMin(sCnt + m).Value = curSumMin(iCnt).Value + l * curBar(k).MinLength
curSumLength(sCnt + m).Note = curSumLength(iCnt).Note & "Bar" & k & "Num" & l
End If
Next l
Next iCnt
sCnt = sCnt + m
End If
k = k + 1
Loop
Call get_MaxResult(curSumLength, sCnt)
'Get conresponded num of bar in this case -> curNum(1 To MaxBar)
For j = 1 To MaxBar
curNum(j) = 0
Next j
j = 2
Do While j <= Len(maxString)
strKey = Mid(maxString, j, 3)
If strKey = "Bar" Then
strAnl = Left(maxString, j - 1)
Call get_NumBar(strAnl)
curNum(tmpBar) = tmpNum
maxString = Right(maxString, Len(maxString) - j + 1)
j = 2
Else
j = j + 1
End If
Loop
Call get_NumBar(maxString)
curNum(tmpBar) = tmpNum
'Get maximun combination in this case -> maxNumUse(curNum, curBar.CurrentNum)
For j = 1 To MaxBar
If curNum(j) <> 0 Then
curFac(j) = curBar(j).CurrentNum \ curNum(j)
Else
curFac(j) = 0
End If
Next j
maxNumUse = maxArray(curFac)
For j = 1 To MaxBar
If maxNumUse >= curFac(j) Then
If curFac(j) > 0 Then
maxNumUse = curFac(j)
End If
End If
Next j
'Write analysis result to sheet
'Writing diameter
'barIndex = get_CurrentIndex()
Cells(cutIndex + iPos, 7) = curBarDiameter
'Writing cut No.
Cells(cutIndex + iPos, 8) = iPos - 3
strDisplay = ""
resLength = 0
For j = 1 To MaxBar
If curNum(j) > 0 Then
strDisplay = strDisplay & curNum(j) & "*[" & curBar(j).Mark & "]+"
resLength = resLength + curNum(j) * curBar(j).Length
End If
Next j
strDisplay = Left(strDisplay, Len(strDisplay) - 1)
Cells(cutIndex + iPos, 9) = strDisplay
Cells(cutIndex + iPos, 10) = maxNumUse
Cells(cutIndex + iPos, 11) = resLength
useLength = useLength + maxLength * maxNumUse
For j = 1 To MaxBar
curBar(j).CurrentNum = curBar(j).CurrentNum - maxNumUse * curNum(j)
Next j
iPos = iPos + 1
Loop
i = i + 1
Loop
'Format cell borders
Range("G" & cutIndex + 4 & ":K" & cutIndex + iPos - 1).Select
Call FormatInputTable
'Number format
Range("K" & cutIndex + 4 & ":K" & cutIndex + iPos - 1).Select
Selection.NumberFormat = "0.000"
cutIndex = cutIndex + iPos - 4
End If
End Sub
Private Sub ControlRemainSteel()
Dim arrDiameter(1 To 15) As Byte
Dim arrMinLength(1 To 15) As Double
Dim arrRealWeigth(1 To 15) As Double
Dim tmpWeight As Double
Dim i%, j%, k%
Dim curMinLength As Double
For i = 1 To 15
arrMinLength(i) = Sheets("Input").Cells(3, i + 8)
arrDiameter(i) = Sheets("Input").Cells(2, i + 8)
Next i

'Clear old data in this sheet
Sheets("Remain").Activate
Range("A4:E65536").Clear
'For i = 1 To 15
'Filter remain steel for next usage
j = 4
k = 0
Do While Trim(Sheets("Result").Cells(j, 9)) <> ""
For i = 1 To 15
If Sheets("Result").Cells(j, 7) = arrDiameter(i) Then
curMinLength = arrMinLength(i)
Exit For
End If
Next i
If maxLength - Sheets("Result").Cells(j, 11) >= curMinLength Then
k = k + 1
Cells(k + 3, 1) = k
Cells(k + 3, 2) = Sheets("Result").Cells(j, 7)
Cells(k + 3, 3) = Sheets("Result").Cells(j, 8)
Cells(k + 3, 4) = Sheets("Result").Cells(j, 10)
Cells(k + 3, 5) = maxLength - Sheets("Result").Cells(j, 11)
End If
j = j + 1
Loop
'Format number
Range("E4:E" & k + 3).Select
Selection.NumberFormat = "0.000"
'Format range
Range("A4:E" & k + 3).Select
Call FormatInputTable
'Get reality weight
j = 4
Do While Trim(Sheets("Result").Cells(j, 9)) <> ""
For i = 1 To 15
If Sheets("Result").Cells(j, 7) = arrDiameter(i) Then
tmpWeight = arrDiameter(i) ^ 2 * constPI / 4 / 10 ^ 6
tmpWeight = tmpWeight * Sheets("Result").Cells(j, 10) * maxLength * 7850
arrRealWeigth(i) = arrRealWeigth(i) + tmpWeight
Exit For
End If
Next i
j = j + 1
Loop
'Writing data
For i = 1 To 15
Cells(i + 3, 9) = arrRealWeigth(i)
Next i
'Next i

End Sub

Public Function minValue(valA, valB) As Double
minValue = valA
If minValue >= valB Then minValue = valB
End Function

Private Sub get_MaxResult(arrBar() As SumLength, arrCnt As Long)
maxResult = arrBar(1).Value
maxString = arrBar(1).Note
Dim i&
For i = 1 To arrCnt
If arrBar(i).Value >= maxResult Then
maxResult = arrBar(i).Value
maxString = arrBar(i).Note
End If
Next i
End Sub

Private Sub get_NumBar(strGet)
tmpNum = 0
tmpBar = 0
Dim i1 As Integer
For i1 = 1 To Len(strGet)
If Mid(strGet, i1, 3) = "Num" Then
tmpBar = Right(Left(strGet, i1 - 1), Len(Left(strGet, i1 - 1)) - 3)
tmpNum = Right(Right(strGet, Len(strGet) - i1 + 1), Len(Right(strGet, Len(strGet) - i1 + 1)) - 3)
Exit For
End If
Next i1

End Sub
Private Function maxArray(arrFac() As Integer) As Integer
maxArray = 0
Dim iArr As Integer
For iArr = LBound(arrFac) To UBound(arrFac)
If maxArray <= arrFac(iArr) Then maxArray = arrFac(iArr)
Next iArr

End Function

Private Function Num2Char(intNum As Integer) As String
Num2Char = ""
Do While intNum > 26
Num2Char = Chr(64 + intNum Mod 26) & Num2Char
intNum = intNum \ 26
Loop
Num2Char = Chr(64 + intNum) & Num2Char
End Function

Private Function get_CurrentIndex()
Dim cIndex As Long
cIndex = 4
Do While Trim(Cells(cIndex, 7)) <> ""
cIndex = cIndex + 1
Loop
get_CurrentIndex = cIndex
End Function


Private Sub FormatInputTable()
Selection.Borders(xlDiagonalDown).LineStyle = xlNone
Selection.Borders(xlDiagonalUp).LineStyle = xlNone
With Selection.Borders(xlEdgeLeft)
.LineStyle = xlContinuous
.Weight = xlThin
.ColorIndex = xlAutomatic
End With
With Selection.Borders(xlEdgeTop)
.LineStyle = xlContinuous
.Weight = xlThin
.ColorIndex = xlAutomatic
End With
With Selection.Borders(xlEdgeBottom)
.LineStyle = xlContinuous
.Weight = xlThin
.ColorIndex = xlAutomatic
End With
With Selection.Borders(xlEdgeRight)
.LineStyle = xlContinuous
.Weight = xlThin
.ColorIndex = xlAutomatic
End With
With Selection.Borders(xlInsideVertical)
.LineStyle = xlContinuous
.Weight = xlHairline
.ColorIndex = xlAutomatic
End With
With Selection.Borders(xlInsideHorizontal)
.LineStyle = xlContinuous
.Weight = xlHairline
.ColorIndex = xlAutomatic
End With
End Sub



 

File đính kèm

Lần chỉnh sửa cuối:
Upvote 0
Xin nhờ cao thủ giúp em vấn đề này với.
Trong WORD em có đoạn văn bản như sau:
< bR>
Chào các bạn
< bR>
Hôm nay trời đẹp
< bR>
Kết thúc

Em muốn viết đoạn code để tự động tìm và thay thế chữ "<bR>" theo quy tắc
Câu 1
Chào các bạn
Câu 2
Hôm nay trời đẹp
Câu 3
Kết thúc

Tức là vừa tìm chữ <bR> vừa đếm xem nó là chữ xuất hiện lần thứ i và thay bằng chữ "Câu i".
Em cần gấp lắm mong được sự cứu giúp của anh em trong diễn đàn lắm ạ.
Em xin chân thành cảm ơn.
 
Lần chỉnh sửa cuối:
Upvote 0
Mình tìm đc đoan code này ở trên mạng:
Sub run_sql_sub(sql)
On Error Resume Next
Set cn = CreateObject("ADODB.Connection")
Set rs = CreateObject("ADODB.Recordset")


With cn
.ConnectionString = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source=" & _
ThisWorkbook.FullName _
& ";Extended Properties=""Excel 12.0 Xml;HDR=YES;IMEX=1"";"
.Open
End With
rs.Open sql, cn


Application.ScreenUpdating = False
ActiveSheet.Range("A2:XFD1048576").ClearContents


For intColIndex = 0 To rs.Fields.Count - 1
Range("A2").Offset(0, intColIndex).Value = rs.Fields(intColIndex).Name
Next


Range("A3").CopyFromRecordset rs
Application.ScreenUpdating = True
rs.Close: cn.Close: Set rs = Nothing: Set cn = Nothing
End Sub

Private Sub Worksheet_Change(ByVal Target As Range)
Dim KeyCells As Range


Set KeyCells = ActiveSheet.Range("A1")

If Not Application.Intersect(KeyCells, Range(Target.Address)) _
Is Nothing Then


If InStr(KeyCells.Value2, "mi_sql") > 0 Then
sql = Right(KeyCells.Value2, Len(KeyCells.Value2) - Len("mi_sql "))
run_sql_sub sql
End If

End If

End Sub

Nhưng mỗi lần cần chạy câu lệnh SQL trong ô A1 lại phải đưa con trỏ lên ô A1 và ấn Enter. Bây giời mình muốn sửa lại để môi lần thay đổi là câu lệnh SQL tự động thực hiện. Cảm ơn
 

File đính kèm

Upvote 0
Nhưng mỗi lần cần chạy câu lệnh SQL trong ô A1 lại phải đưa con trỏ lên ô A1 và ấn Enter. Bây giời mình muốn sửa lại để môi lần thay đổi là câu lệnh SQL tự động thực hiện. Cảm ơn
Bạn nói rõ hơn, mỗi lần thay đổi là thay đổi thế nào không vậy, tức là thay đổi ở các ô khác hay sao?
- Nếu bạn muốn thay đổi 1 vùng từ A1 đến B10 đi chẳng hạn thì code thực hiện: bạn chỉ cần thay dòng: Set KeyCells = ActiveSheet.Range("A1") ====> Set KeyCells = ActiveSheet.Range("A1:B10"). Nói chung bạn chỉ cần thay đổi trong đó vùng bạn tác động
 
Upvote 0
Mình tìm đc đoan code này ở trên mạng:
Sub run_sql_sub(sql)
On Error Resume Next
Set cn = CreateObject("ADODB.Connection")
Set rs = CreateObject("ADODB.Recordset")


With cn
.ConnectionString = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source=" & _
ThisWorkbook.FullName _
& ";Extended Properties=""Excel 12.0 Xml;HDR=YES;IMEX=1"";"
.Open
End With
rs.Open sql, cn


Application.ScreenUpdating = False
ActiveSheet.Range("A2:XFD1048576").ClearContents


For intColIndex = 0 To rs.Fields.Count - 1
Range("A2").Offset(0, intColIndex).Value = rs.Fields(intColIndex).Name
Next


Range("A3").CopyFromRecordset rs
Application.ScreenUpdating = True
rs.Close: cn.Close: Set rs = Nothing: Set cn = Nothing
End Sub

Private Sub Worksheet_Change(ByVal Target As Range)
Dim KeyCells As Range


Set KeyCells = ActiveSheet.Range("A1")

If Not Application.Intersect(KeyCells, Range(Target.Address)) _
Is Nothing Then


If InStr(KeyCells.Value2, "mi_sql") > 0 Then
sql = Right(KeyCells.Value2, Len(KeyCells.Value2) - Len("mi_sql "))
run_sql_sub sql
End If

End If

End Sub

Nhưng mỗi lần cần chạy câu lệnh SQL trong ô A1 lại phải đưa con trỏ lên ô A1 và ấn Enter. Bây giời mình muốn sửa lại để môi lần thay đổi là câu lệnh SQL tự động thực hiện. Cảm ơn

gõ HCM,DANANG,HANOI vào ô A1
Mã:
Private Sub Worksheet_Change(ByVal Target As Range)
    
    If Target.Address = "$A$1" Then
            sql = "select * from [vpp] where region=" & "'" & [A1] & "'"
            run_sql_sub sql
    End If
    
End Sub
 
Upvote 0
Các bác cho em hỏi 1 chút ạ. Trong Macro setting của em, sao cái dấu tích trust access to the vba project object model - Nó bị mờ đi ạ, k tích được, cũng k bỏ tích được. Như vậy liệu có ảnh hưởng đến các code VBA của mình ko ạ
 
Upvote 0
Các bác cho em hỏi 1 chút ạ. Trong Macro setting của em, sao cái dấu tích trust access to the vba project object model - Nó bị mờ đi ạ, k tích được, cũng k bỏ tích được. Như vậy liệu có ảnh hưởng đến các code VBA của mình ko ạ

Cũng chẳng sao cả, nhưng nếu bạn muốn nó "bình thường" trở lại thì làm như sau:
- Đóng toàn bộ Excel
- Bấm tổ hợp phím Windows + R (lá cờ windows và phím R)
- Gõ REGEDIT vào khung Open rồi Enter
- Duyệt tới đường dẫn:
Mã:
HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Office\[COLOR=#ff0000]16.0[/COLOR]\Excel\Security
(Con số 16.0 màu đỏ ở trên là tùy theo phiên bản Office nha)
- Nhìn khung bên phải, nếu thấy mục có tên AccessVBOM thì xóa phéng nó đi
- Khởi động Excel và kiểm tra lại mục "Trust access.... "
 
Upvote 0
Cũng chẳng sao cả, nhưng nếu bạn muốn nó "bình thường" trở lại thì làm như sau:
- Đóng toàn bộ Excel
- Bấm tổ hợp phím Windows + R (lá cờ windows và phím R)
- Gõ REGEDIT vào khung Open rồi Enter
- Duyệt tới đường dẫn:
Mã:
HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Office\[COLOR=#ff0000]16.0[/COLOR]\Excel\Security
(Con số 16.0 màu đỏ ở trên là tùy theo phiên bản Office nha)
- Nhìn khung bên phải, nếu thấy mục có tên AccessVBOM thì xóa phéng nó đi
- Khởi động Excel và kiểm tra lại mục "Trust access.... "
Theo đường dẫn của bác NDU thì nó hem ra ạ, mà e find trong regitry thì cái AccessVBOM nó nằm ở đường dẫn này ạ: HKEY_LOCAL_MACHINE\SOFTWARE\Policies\Microsoft\Office\15.0\Excel\Security
Thêm cái mục lớn là Policies nữa ạ. e Đã xóa rùi, mà trong Excel - Marco seting - Cái trust access to the vba project object model nó vẫn bị mờ ạ.
Nhưng bác NDU đã nói k vấn đề gì thì ok ,kệ bố nó :D. Thank bác nhìu. Chúc bác ngày cuối tuần vui vẻ ạ --=0
 
Upvote 0
Thuộc tính End trong VBA: [C65536].End(3)(1, 2). Các bác cho em hỏi, cái phần e bôi đậm nghĩa là sao vậy ạ !
 
Upvote 0
Thuộc tính End trong VBA: [C65536].End(3)(1, 2). Các bác cho em hỏi, cái phần e bôi đậm nghĩa là sao vậy ạ !

Truy xuất na ná như hàm INDEX ấy
Giả sử [C65536].End(3) ra được kết quả là cell C15 đi nha. Vậy cái tô đậm kia sẽ index 1 dòng 2 cột, ra kết quả là cell D15
Tổng quát:
Tham chiếu(m, n) sẽ cho kết quả cell có dòng thứ m, cột thứ n tính từ cell tham chiếu
Lưu ý:
- Tại vị trí cell tham chiếu được tính là dòng 1, cột 1
- m và n có thể có giá trị âm
 
Lần chỉnh sửa cuối:
Upvote 0
Truy xuất na ná như hàm INDEX ấy
Giả sử [C65536].End(3) ra được kết quả là cell C15 đi nha. Vậy cái tô đậm kia sẽ index 1 dòng 2 cột, ra kết quả là cell D15
Tổng quát:
Tham chiếu(m, n) sẽ cho kết quả cell có dòng thứ m, cột thứ n tính từ cell tham chiếu
Lưu ý:
- Tại vị trí cell tham chiếu được tính là dòng 1, cột 1
- m và n có thể có giá trị âm


Vậy mình có thể dùng offset ko ạ. [C65536].end(3).offset(m,n). 2 cách này có khác nhau ko ạ
 
Upvote 0
Trong Sub này

Sub TinhTien()
On Error Resume Next
For Each cls In Range([c3], [c65536].End(3))
If cls > 0 Then
cls(1, 2) = Sheets("Don Gia").Cells.Find(cls(1, 0), , , 2)(1, 2)
cls(1, 3) = cls * cls(1, 2)
End If
Next
End Sub

Cho e hỏi với ạ: Tại vị trí em bôi đậm, e chưa hiểu điều kiện cần tìm này là gì ạ !
 
Upvote 0
Trong Sub này

Sub TinhTien()
On Error Resume Next
For Each cls In Range([c3], [c65536].End(3))
If cls > 0 Then
cls(1, 2) = Sheets("Don Gia").Cells.Find(cls(1, 0), , , 2)(1, 2)
cls(1, 3) = cls * cls(1, 2)
End If
Next
End Sub

Cho e hỏi với ạ: Tại vị trí em bôi đậm, e chưa hiểu điều kiện cần tìm này là gì ạ !
Giả sử cls là ô C7 thì cls(1,0) là ô B7.
 
Upvote 0
Truy xuất na ná như hàm INDEX ấy
Giả sử [C65536].End(3) ra được kết quả là cell C15 đi nha. Vậy cái tô đậm kia sẽ index 1 dòng 2 cột, ra kết quả là cell D15
Tổng quát:
Tham chiếu(m, n) sẽ cho kết quả cell có dòng thứ m, cột thứ n tính từ cell tham chiếu
Lưu ý:
- Tại vị trí cell tham chiếu được tính là dòng 1, cột 1
- m và n có thể có giá trị âm
Xin thầy chia sẽ thêm là: tham chiếu kiểu này và offset cơ bản có cùng bản chất, vậy sử dụng cái nào sẽ tối ưu hơn ạ, và thầy thường sử dụng phương pháp nào, em cám ơn
 
Upvote 0
Dear all,

Em có viết 1 file báo cáo công ty bằng VBA khi chạy trên máy ở nhà thì code chạy ổn định, Nhưng khi sang máy khác bị lỗi ở modul 6, bước cuối cùng tổng hợp báo cáo. Mong mọi người xem xét chỉ giúp em lỗi của file này RUN TIME ERRO 7 OUT OF MEMORY. (Do file này nặng em tải nên drive, các anh chị tải về xem giúp em)
Rát mong nhận được sự giúp đỡ của mọi người. Em xin chân thành cảm ơn.

https://drive.google.com/file/d/0B7_P2xWKkzz7dWhoU3JHck9JZzA/view
 
Upvote 0
Xin thầy chia sẽ thêm là: tham chiếu kiểu này và offset cơ bản có cùng bản chất, vậy sử dụng cái nào sẽ tối ưu hơn ạ, và thầy thường sử dụng phương pháp nào, em cám ơn

Nhìn thì có vẻ giống! Tức nếu viết Range("C7")(2, 2) thì các bạn nghĩ nó tương đương với Range("C7").Offset(1,1) đúng không?
Nếu vậy thì người ta "đẻ" thêm cái kiểu (2,2) kia làm gì cho nhức đầu
???!!!
Ta hãy làm cuộc thí nghiệm thế này:
- Quét chọn C7:G15 rồi thực hiện lệnh Merge chúng lại với nhau
- Vào cửa sổ VBA, bấm Ctrl + G (mở cửa sổ Immediate)
- Gõ vào khung Immediate dòng lệnh ?Range("C7")(2,2).Address rồi Enter phát, ta nhận được kết quả $D$8 (Ổn đúng không?)
- Tiếp theo gõ vào khung Immediate lệnh ?Range("C7").Offset(1,1).Address rồi Enter phát, ta nhận được kết quả $H$16 (bất ngờ quá đúng không?)

--------------------------
Vậy ta có thể tạm kết luận rằng:
- Kiểu viết Range("...").Offset(m-1,n-1) sẽ giống với kiểu Range("...")(m,n) cho trường hợp cell thường chưa Merge
- Kiểu viết Range("...").Offset(....) tương đương với thao tác chọn 1 cell rồi dùng các phím mũi tên để di chuyển. Chẳng hạn tình huống trên, nếu chọn C7 (đã Merge) rồi bấm phím mũi tên xuống và mũi tên phải cùng lúc, activeCell cũng sẽ được di chuyển đến H16 ---> Đó chính là Range("C7").Offset(1,1) đấy
- Ngoài cells bị merge ra, Offset còn gặp rắc rối tương tự khi có dòng ẩn, cột ẩn hoặc bảng tính có fillter (nó sẽ "nhảy" linh tinh khiến ta ngơ ngác không hiểu mình sai ở đâu)
- Kiểu viết Range(m,n) luôn luôn cho kết quả đúng như những gì mình nghĩ trong đầu, bất kể cell có bị merge, bị ẩn hay filter
--------------------------
Hiểu được sự khác nhau giữa 2 cách viết rồi, các bạn quyết định xài cái nào là.. tùy tình huống. Riêng tôi, ít khi thích xài Offset
 
Lần chỉnh sửa cuối:
Upvote 0
Nhìn thì có vẻ giống! Tức nếu viết Range("C7")(2, 2) thì các bạn nghĩ nó tương đương với Range("C7").Offset(1,1) đúng không?
Nếu vậy thì người ta "đẻ" thêm cái kiểu (2,2) kia làm gì cho nhức đầu
???!!!
Ta hãy làm cuộc thí nghiệm thế này:
- Quét chọn C7:G15 rồi thực hiện lệnh Merge chúng lại với nhau
- Vào cửa sổ VBA, bấm Ctrl + G (mở cửa sổ Immediate)
- Gõ vào khung Immediate dòng lệnh ?Range("C7")(2,2).Address rồi Enter phát, ta nhận được kết quả $D$8 (Ổn đúng không?)
- Tiếp theo gõ vào khung Immediate lệnh ?Range("C7").Offset(1,1).Address rồi Enter phát, ta nhận được kết quả $H$16 (bất ngờ quá đúng không?)

--------------------------
Vậy ta có thể tạm kết luận rằng:
- Kiểu viết Range("...").Offset(m-1,n-1) sẽ giống với kiểu Range("...")(m,n) cho trường hợp cell thường chưa Merge
- Kiểu viết Range("...").Offset(....) tương đương với thao tác chọn 1 cell rồi dùng các phím mũi tên để di chuyển. Chẳng hạn tình huống trên, nếu chọn C7 (đã Merge) rồi bấm phím mũi tên xuống và mũi tên phải cùng lúc, activeCell cũng sẽ được di chuyển đến H16 ---> Đó chính là Range("C7").Offset(1,1) đấy
- Ngoài cells bị merge ra, Offset còn gặp rắc rối tương tự khi có dòng ẩn, cột ẩn hoặc bảng tính có fillter (nó sẽ "nhảy" linh tinh khiến ta ngơ ngác không hiểu mình sai ở đâu)
- Kiểu viết Range(m,n) luôn luôn cho kết quả đúng như những gì mình nghĩ trong đầu, bất kể cell có bị merge, bị ẩn hay filter
--------------------------
Hiểu được sự khác nhau giữa 2 cách viết rồi, các bạn quyết định xài cái nào là.. tùy tình huống. Riêng tôi, ít khi thích xài Offset
Dạ em cám ơn thầy rất nhiều ạ, đúng là chỉ có trải nghiệm nhiều mới biết được những cái này.
 
Upvote 0
Có Anh/Chị nào giúp em set pass cho file PDF sau khi export ra không ạ?

Em xin đính kèm file ở dưới, trong File e đã xuất ra dc file PDF rồi, nhưng không có set pass dc ạ
 

File đính kèm

Upvote 0
Có Anh/Chị nào giúp em set pass cho file PDF sau khi export ra không ạ?

Em xin đính kèm file ở dưới, trong File e đã xuất ra dc file PDF rồi, nhưng không có set pass dc ạ
Bạn đã thử bài này chưa?

http://www.giaiphapexcel.com/forum/showthread.php?120467-Macro-save-file-với-định-dạng-pdf-có-pass

Mình cũng đang hóng xem có cách nào khác không đây. Search nhiều rùi nhưng câu trả lời mình thấy chỉ có như link mình gửi bạn là có vẻ ok.
 
Upvote 0
Giới hạn vùng thao tác?

Xin chào tất cả các bạn,

Oanh Thơ muốn sử dung 1 đoạn code hoạt động trong sự kiện bên dưới, với điều kiện là khi thao tác trong cộ E từ dòng số 10 nghĩa là từ E10 xuống đến dòng cuối cùng trong cột E có dữ lieu thì sự kiện mới có tác dụng còn ngoài điều kiện trên thì code không hoạt động.

Mã:
Private Sub Worksheet_BeforeDoubleClick(ByVal Target As Range, Cancel As Boolean)
        
End Sub

Rất mong nận được sự giúp đỡ từ các bạn.
Xin cảm ơn các bạn nhiều
 
Upvote 0
Xin chào tất cả các bạn,

Oanh Thơ muốn sử dung 1 đoạn code hoạt động trong sự kiện bên dưới, với điều kiện là khi thao tác trong cộ E từ dòng số 10 nghĩa là từ E10 xuống đến dòng cuối cùng trong cột E có dữ lieu thì sự kiện mới có tác dụng còn ngoài điều kiện trên thì code không hoạt động.

Mã:
Private Sub Worksheet_BeforeDoubleClick(ByVal Target As Range, Cancel As Boolean)
        
End Sub

Rất mong nận được sự giúp đỡ từ các bạn.
Xin cảm ơn các bạn nhiều
Không biết đúng ý không?
Mã:
If Not Intersect(Target, Range("E10:E" & Range("E65000").End(xlUp).Row)) Is Nothing Then
    'code cua ban.
End If
 
Upvote 0
rivate Sub Worksheet_Calculate()
Static oldval
If Range("A2").Value <> oldval Then
oldval = Range("A2")
Call AutoNhatKy
End If
End SubPrivate Sub Worksheet_Calculate()
Static oldval
If Range("A2").Value <> oldval Then
oldval = Range("A2")
Call AutoNhatKy
End If
End Sub
-------------------------------
Mình có đoạn code gọi Sub tự động, làm thế nào để khi đang đứng ở 1 sheet khác code chạy mà nó không bị quay lại Sheet chạy code
 
Upvote 0
rivate Sub Worksheet_Calculate()
Static oldval
If Range("A2").Value <> oldval Then
oldval = Range("A2")
Call AutoNhatKy
End If
End SubPrivate Sub Worksheet_Calculate()
Static oldval
If Range("A2").Value <> oldval Then
oldval = Range("A2")
Call AutoNhatKy
End If
End Sub
-------------------------------
Mình có đoạn code gọi Sub tự động, làm thế nào để khi đang đứng ở 1 sheet khác code chạy mà nó không bị quay lại Sheet chạy code

alibaba chứ có phải "40 tên cướp" đâu mà thích thả bom diễn đàn vậy ?

http://www.giaiphapexcel.com/forum/...1-code-về-công-thức-mảng!&p=756874#post756874

http://www.giaiphapexcel.com/forum/...!-có-file-và-ảnh-đính-kèm&p=756877#post756877
 
Upvote 0
Upvote 0
Upvote 0
Bác giúp em vấn đề này với ạ!

vấn đề khó hay dễ tôi đều làm nếu tôi biết , chỉ tiếc là tôi không giao thiệp với các thành phần không tôn trọng nội quy , hễ thích thì gửi bài viết cùng 1 nội dung ở nhiều nơi , cho nên bạn phải chờ thành viên khác rồi .
 
Upvote 0
vấn đề khó hay dễ tôi đều làm nếu tôi biết , chỉ tiếc là tôi không giao thiệp với các thành phần không tôn trọng nội quy , hễ thích thì gửi bài viết cùng 1 nội dung ở nhiều nơi , cho nên bạn phải chờ thành viên khác rồi .
Dạ vâng! em sẽ đọc lại Nội Quy và chấp hành. Cảm ơn bác đã nhắc nhở
 
Upvote 0
Nhờ mọi người giải thích giúp đoạn Code lưu File dưới đây

Em nhờ mọi người giải thích giúp e những phần bôi đỏ dưới đây :

Mã:
ActiveWorkbook.SaveAs fileName:=path & "\" & fileName & ".xls",FileFormat:=xlExcel8, [COLOR=#ff0000][B]Password:="", WriteResPassword:="",[/B][/COLOR]

 [COLOR=#ff0000][B]ReadOnlyRecommended:=False[/B][/COLOR], CreateBackup:=False

Em xin cảm ơn ạ !
 
Upvote 0
Em nhờ mọi người giải thích giúp e những phần bôi đỏ dưới đây :

Mã:
ActiveWorkbook.SaveAs fileName:=path & "\" & fileName & ".xls",FileFormat:=xlExcel8, [COLOR=#ff0000][B]Password:="", WriteResPassword:="",_ [/B][/COLOR]
  [COLOR=#ff0000][B]ReadOnlyRecommended:=False[/B][/COLOR], CreateBackup:=False

Em xin cảm ơn ạ !


Password:=""
'Đặt mật khẩu Open file

WriteResPassword:=""
'Đặt mật khẩu Edit file

ReadOnlyRecommended:=False
'Thiết lập chế độ chỉ đọc, False là không đặt chế độ chỉ đọc, True là bật chế độ chỉ đọc cho file
 
Upvote 0
Em nhờ mọi người giải thích giúp e những phần bôi đỏ dưới đây :

Mã:
ActiveWorkbook.SaveAs fileName:=path & "\" & fileName & ".xls",FileFormat:=xlExcel8, [COLOR=#ff0000][B]Password:="", WriteResPassword:="",[/B][/COLOR]

 [COLOR=#ff0000][B]ReadOnlyRecommended:=False[/B][/COLOR], CreateBackup:=False

Em xin cảm ơn ạ !

Nếu chỗ màu đỏ = "" và = False thì xóa luôn đi, khỏi giải thích. Chứ ghi vào mà không có tác dụng gì thì ghi làm gì cho thêm năng đầu suy nghĩ. Đợi khi nào dùng tới sẽ nghiên cứu
 
Upvote 0
Cảm ơn anh benfaint và chú Ndu ạ. Ủa mà sao không thấy nút cảm ơn trên diễn đàn nữa đâu ta ....

Nếu chỗ màu đỏ = "" và = False thì xóa luôn đi, khỏi giải thích. Chứ ghi vào mà không có tác dụng gì thì ghi làm gì cho thêm năng đầu suy nghĩ. Đợi khi nào dùng tới sẽ nghiên cứu

Code này hổng phải con viết đâu chú, cái này của người khác họ lấy ở đâu đó rồi nhờ con giải thích dùm ... về phần này thì con cũng không rành lắm nên phải hỏi lại cho chắc chắn ạ
 
Upvote 0
Nhờ mọi người giải thích giúp e đoạn Code này với ạ, đoạn Code này để tạo ra 5 File khác:

Trong file đính kèm e thấy có đoạn Code:
Mã:
   Sheets(Array("Sheet1")).Select
    Sheets(Array("Sheet1")).Copy

Nhưng về sau không thấy Paste ở đâu ... mà xóa 2 dòng Code trên đi thì nó lại chỉ tạo ra mỗi 1 File ...Em không hiểu là sao nữa ...
 

File đính kèm

Lần chỉnh sửa cuối:
Upvote 0
Nói chung mọi người giải thích sơ qua về đoạn code này giúp e vs được không ạ:
Mã:
Sub SplitFile(rptTitle As String, fileName As String, path As String)
    
    Range("B2") = rptTitle

    Sheets(Array("Sheet1")).Select  
    Sheets(Array("Sheet1")).Copy  [COLOR=#ff0000][B] ' Chỗ này Copy xong nhưng không thấy Paste vô đâu cả  ... ????'[/B][/COLOR]
    
    Range("E7:F8").Select
    Selection.Copy
    Selection.PasteSpecial Paste:=xlPasteValues, Operation:=xlNone, SkipBlanks:=False, Transpose:=False


    Application.DisplayAlerts = False
    ActiveWorkbook.SaveAs fileName:=path & "\" & fileName & ".xls", _
        FileFormat:=xlExcel8, Password:="", WriteResPassword:="", _
        ReadOnlyRecommended:=False, CreateBackup:=False
    
    Application.DisplayAlerts = True
    ActiveWindow.Close
  
End Sub
----------------------------------------------------------------------------------------------------------

Sub Main()
    Dim rptTitle As String, fileName As String, i As Integer, j As Integer, path As String
    path = ThisWorkbook.path
    
    i = 2
    j = 1
    Set WS = ThisWorkbook.Sheets("MA_NV")
    
    Do Until IsEmpty(WS.Cells(i, j))
    rptTitle = WS.Cells(i, j)
    fileName = WS.Cells(i, j + 1)

    SplitFile rptTitle, fileName, path ' -->[COLOR=#ff0000][B] tại sao chổ này phải viết vầy mà không thể viết thế này : SplitFile(rptTitle As String, fileName As String, path As String) '[/B][/COLOR]
    
    i = i + 1
    
    Loop

End Sub
-----------------------------------------------------------------------------------------------------
Sub chonmayin()
Application.Dialogs(xlDialogPrinterSetup).Show
End Sub
'phai chay cai nay truoc de chon may in
 
Lần chỉnh sửa cuối:
Upvote 0
Nói chung mọi người giải thích sơ qua về đoạn code này giúp e vs được không ạ:
Mã:
Sub SplitFile(rptTitle As String, fileName As String, path As String)
    
    Range("B2") = rptTitle

    Sheets(Array("Sheet1")).Select  
    Sheets(Array("Sheet1")).Copy  [COLOR=#ff0000][B] ' Chỗ này Copy xong nhưng không thấy Paste vô đâu cả  ... ????'[/B][/COLOR]
    
    Range("E7:F8").Select
    Selection.Copy
    Selection.PasteSpecial Paste:=xlPasteValues, Operation:=xlNone, SkipBlanks:=False, Transpose:=False


    Application.DisplayAlerts = False
    ActiveWorkbook.SaveAs fileName:=path & "\" & fileName & ".xls", _
        FileFormat:=xlExcel8, Password:="", WriteResPassword:="", _
        ReadOnlyRecommended:=False, CreateBackup:=False
    
    Application.DisplayAlerts = True
    ActiveWindow.Close
  
End Sub

bạn xóa hết tất cả các dòng từ sau lệnh
Mã:
Sheets(Array("Sheet1")).Copy
trở xuống là biết ngay nó copy đi đâu thôi mà .
 
Upvote 0
Em nhờ mọi người dịch cho em đoạn code này ạ:

Option Explicit

Public Sub GPE()
Dim Dic As Object, Ws As Worksheet, sArr(), dArr(1 To 100, 1 To 4)
Dim I As Long, J As Long, K As Long, Rws As Long, Tem As String
Set Dic = CreateObject("Scripting.Dictionary")
For Each Ws In Worksheets
If Ws.Name <> "Data" Then
sArr = Ws.Range("A4", Ws.Range("A4").End(xlDown)).Resize(, 5).Value
For I = 1 To UBound(sArr)
Tem = sArr(I, 1) & "#" & sArr(I, 2) & "#" & sArr(I, 5)
If Not Dic.Exists(Tem) Then
K = K + 1
Dic.Add Tem, K
dArr(K, 1) = sArr(I, 1)
dArr(K, 2) = sArr(I, 2)
dArr(K, 4) = sArr(I, 5)
End If
Rws = Dic.Item(Tem)
dArr(Rws, 3) = dArr(Rws, 3) + sArr(I, 4)
Next I
End If
Next Ws
With Sheets("Data")
.Range("C5:F100").ClearContents
.Range("C5:F5").Resize(K) = dArr
.Range("A5:F5").Resize(K).Borders.LineStyle = 1
End With
Set Dic = Nothing
End Sub

Em cảm ơn!
 
Upvote 0
Em nhờ mọi người dịch cho em đoạn code này ạ:

Option Explicit

Public Sub GPE()
Dim Dic As Object, Ws As Worksheet, sArr(), dArr(1 To 100, 1 To 4)
Dim I As Long, J As Long, K As Long, Rws As Long, Tem As String
Set Dic = CreateObject("Scripting.Dictionary")
For Each Ws In Worksheets
If Ws.Name <> "Data" Then
sArr = Ws.Range("A4", Ws.Range("A4").End(xlDown)).Resize(, 5).Value
For I = 1 To UBound(sArr)
Tem = sArr(I, 1) & "#" & sArr(I, 2) & "#" & sArr(I, 5)
If Not Dic.Exists(Tem) Then
K = K + 1
Dic.Add Tem, K
dArr(K, 1) = sArr(I, 1)
dArr(K, 2) = sArr(I, 2)
dArr(K, 4) = sArr(I, 5)
End If
Rws = Dic.Item(Tem)
dArr(Rws, 3) = dArr(Rws, 3) + sArr(I, 4)
Next I
End If
Next Ws
With Sheets("Data")
.Range("C5:F100").ClearContents
.Range("C5:F5").Resize(K) = dArr
.Range("A5:F5").Resize(K).Borders.LineStyle = 1
End With
Set Dic = Nothing
End Sub

Em cảm ơn!

đang hỏi ở đây thì cứ vào đây mà hỏi

http://www.giaiphapexcel.com/forum/...Tìm-hiểu-về-mảng-qua-code&p=757119#post757119
 
Upvote 0

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

Back
Top Bottom