ExcelHome技术论坛

 找回密码
 免费注册

QQ登录

只需一步,快速开始

快捷登录

搜索
EH技术汇-专业的职场技能充电站 妙哉!函数段子手趣味讲函数 Excel服务器-会Excel,做管理系统 效率神器,一键搞定繁琐工作
HR薪酬管理数字化实战 Excel 2021函数公式学习大典 Excel数据透视表实战秘技 打造核心竞争力的职场宝典
让更多数据处理,一键完成 数据工作者的案头书 免费直播课集锦 ExcelHome出品 - VBA代码宝免费下载
用ChatGPT与VBA一键搞定Excel WPS表格从入门到精通 Excel VBA经典代码实践指南
楼主: 840205910

[求助] 求先进先出法仓库账的代码

[复制链接]

TA的精华主题

TA的得分主题

 楼主| 发表于 2012-7-14 10:52 | 显示全部楼层
[广告] VBA代码宝 - VBA编程加强工具 · VBA代码随查随用  · 内置多项VBA编程加强工具       ★ 免费下载 ★      ★使用手册
不知道我注释得对不对?望各位老师纠正指教!

TA的精华主题

TA的得分主题

发表于 2012-7-15 18:56 | 显示全部楼层
  1. Option Explicit
  2. Private Sub Worksheet_Change(ByVal Target As Range)
  3.     If Target.Column = 9 And Target.Count = 1 Then
  4.         Dim arr As Variant
  5.         Dim d As Object
  6.         Dim nt As Long
  7.         Dim smin As Long, smax As Long
  8.         Dim i As Integer, j As Integer
  9.         Dim hs As Variant
  10.         Dim ssum As Long, tsum As Long
  11.         Dim minr As Integer, maxr As Integer
  12.         Application.EnableEvents = False
  13.         arr = Range("f5:n" & [a65536].End(3).Row)
  14.         nt = Application.Sum(Range([i5], Target.Offset(-1)))
  15.         If nt + Target.Value > Application.Sum([f:f]) Then GoTo ll
  16.         If Target.Value = "" Then GoTo ll
  17.         Set d = CreateObject("Scripting.Dictionary")
  18.         For i = 1 To UBound(arr)
  19.             If Len(arr(i, 1)) Then d(i) = arr(i, 2)
  20.         Next
  21.         hs = d.keys
  22.         For j = 0 To UBound(hs)
  23.             If nt >= smin Then smin = smin + arr(hs(j), 1): minr = j
  24.             If nt + Target.Value >= smax Then smax = smax + arr(hs(j), 1): maxr = j
  25.         Next
  26.         If smin - nt >= Target.Value Then
  27.             Target.Offset(, 1).Value = arr(hs(minr), 2)
  28.             Target.Offset(, 2).Value = Target.Offset(, 1).Value * Target.Value
  29.         Else
  30.             ssum = ssum + (smin - nt) * arr(hs(minr), 2)
  31.             tsum = Target.Value - (smin - nt)
  32.             For i = minr + 1 To maxr
  33.                 If tsum > arr(hs(i), 1) Then
  34.                     ssum = ssum + arr(hs(i), 1) * arr(hs(i), 2)
  35.                     tsum = tsum - arr(hs(i), 1)
  36.                 Else
  37.                     ssum = ssum + tsum * arr(hs(i), 2)
  38.                 End If
  39.             Next
  40.             Target.Offset(, 1).Value = ssum / Target.Value
  41.             Target.Offset(, 2).Value = ssum
  42.             End If
  43.             Target.Offset(, 3).Resize(, 3).FormulaR1C1 = Array("=SUM(R5C6:RC[-6])-SUM(R5C9:RC[-3])", "=RC[1]/RC[-1]", "=SUM(R5C8:RC[-6])-SUM(R5C11:RC[-3])")
  44.     End If
  45.     Application.EnableEvents = True
  46.     Set d = Nothing
  47.     Exit Sub
  48. ll:
  49.     Target.Value = "": Target.Resize(, 6).Value = ""
  50.      Application.EnableEvents = True
  51. End Sub
复制代码

评分

2

查看全部评分

TA的精华主题

TA的得分主题

发表于 2012-7-15 18:58 | 显示全部楼层

TA的精华主题

TA的得分主题

发表于 2012-7-16 00:12 | 显示全部楼层
本帖最后由 白云2011 于 2012-7-16 00:16 编辑

不知道那里还有点问题。后面那行不对。
开始我想是否需要建立保留99批次数组.可能做错了。
Sub s()
Dim i&, j, ar
ar = Range("A1:R" & [I65536].End(3).Row + 1)
ar(4, 12) = 0: ar(4, 13) = 0: ar(4, 14) = 0
ar(5, 15) = ar(5, 6): ar(5, 16) = ar(5, 7)
For i = 5 To UBound(ar) - 1
ar(i, 15) = Abs(ar(i - 1, 12) - ar(i, 9))  '先进部分(库存
ar(i, 16) = ar(i - 1, 13)  '0
If ar(i, 15) = 0 Then j = 0 Else j = 2
ar(i, 15 + j) = ar(i, 6)  '后进部分(入库
ar(i, 16 + j) = ar(i, 7)
If ar(i, 6) <> "" Then ar(i, 8) = ar(i, 7) * ar(i, 6) '[购进]金额
   ar(i, 12) = ar(i - 1, 12) + ar(i, 6) - ar(i, 9) '[库存]剩余数量
   If ar(i, 9) = "" Then '没出库 [库存] 金额 = 遗留+入库。
   ar(i, 14) = ar(i - 1, 14) + ar(i, 8) '[库存]  金额
   ar(i, 13) = Round(ar(i, 14) / ar(i, 12), 2) '[库存]单价
Else '出库 先处理 [领用]单价
   If ar(i - 1, 15) >= ar(i, 9) Then '如果先进货量充足
      ar(i, 10) = ar(i - 1, 13) '[领用]单价
      ar(i, 11) = ar(i, 9) * ar(i, 10) '[领用]金额
      ar(i, 14) = ar(i - 1, 14) + ar(i, 8) - ar(i, 11) '[库存]金额
      ar(i, 13) = Round(ar(i, 14) / ar(i, 12), 2) '[库存]单价
   Else ''''''''用到先进和先出
      j = (ar(i, 9) - ar(i - 1, 15)) * ar(i - 1, 18)
      ar(i, 11) = Round(ar(i - 1, 15) * ar(i - 1, 16) + j, 2) '[领用]单价
   End If
   ar(i, 10) = Round(ar(i, 11) / ar(i, 9), 2) '[领用]金额
   ar(i, 14) = ar(i - 1, 14) + ar(i, 8) - ar(i, 11) '[库存]金额
   ar(i, 13) = Round(ar(i, 14) / ar(i, 12), 2) '[库存]单价
End If
Next
ar(4, 12) = "数量": ar(4, 13) = "单价": ar(4, 14) = "金额"
[A1].Resize(UBound(ar), 18) = ar
End Sub

评分

1

查看全部评分

TA的精华主题

TA的得分主题

 楼主| 发表于 2012-7-16 07:55 | 显示全部楼层
AVEL 发表于 2012-7-15 18:56

谢谢AVEL老师,我仔细阅读研究一下。不过还是想请你帮我注释一下10楼的代码关键部分,谢谢!

TA的精华主题

TA的得分主题

 楼主| 发表于 2012-7-16 08:06 | 显示全部楼层
[广告] Excel易用宝 - 提升Excel的操作效率 · Excel / WPS表格插件       ★免费下载 ★       ★ 使用帮助
白云2011 发表于 2012-7-16 00:12
不知道那里还有点问题。后面那行不对。
开始我想是否需要建立保留99批次数组.可能做错了。
Sub s()

你的附件不一样?能上传你的附件吗?

TA的精华主题

TA的得分主题

发表于 2012-7-16 09:14 | 显示全部楼层
[广告] Excel易用宝 - 提升Excel的操作效率 · Excel / WPS表格插件       ★免费下载 ★       ★ 使用帮助
试试,A 列不为空就可自动计算

&u.rar

8.91 KB, 下载次数: 78

TA的精华主题

TA的得分主题

 楼主| 发表于 2012-7-16 10:14 | 显示全部楼层
AVEL 发表于 2012-7-15 18:56

老师,是不是这样理解?

Private Sub Worksheet_Change(ByVal Target As Range)
Dim lie, ha
lie = Target.Column
ha = Target.Row
If lie = 7 Or lie = 6 Then
Cells(ha, 8) = Cells(ha, 6) * Cells(ha, 7)
End If

If lie = 8 Then
If Cells(ha, 6) = 0 Then
Cells(ha, 7) = 0
Else
Cells(ha, 7) = Cells(ha, 8) / Cells(ha, 6)
End If
End If





    If Target.Column = 9 And Target.Count = 1 Then
        Dim arr As Variant
        Dim d As Object
        Dim nt As Long
        Dim smin As Long, smax As Long
        Dim i As Integer, j As Integer
        Dim hs As Variant
        Dim ssum As Long, tsum As Long
        Dim minr As Integer, maxr As Integer
        Application.EnableEvents = False
        arr = Range("f5:n" & [a65536].End(3).Row) '把九列数据装入数组
        nt = Application.Sum(Range([i5], Target.Offset(-1))) '本次领用前的所有领用之和
        If nt + Target.Value > Application.Sum([f:f]) Then GoTo ll '若领用之和大于购进之和则从目标列处起后6列为空
        If Target.Value = "" Then GoTo ll '若目标值为空则从目标列处起后6列为空
        Set d = CreateObject("Scripting.Dictionary") '字典
        For i = 1 To UBound(arr) '循环
            If Len(arr(i, 1)) Then d(i) = arr(i, 2) '写入字典
        Next
        hs = d.keys '关键词
        For j = 0 To UBound(hs)
            If nt >= smin Then smin = smin + arr(hs(j), 1): minr = j '本次领用前的所有领用之和大于等于前批购进之和?******
            If nt + Target.Value >= smax Then smax = smax + arr(hs(j), 1): maxr = j '所有领用之和大于等于总购进之和?************
        Next
        If smin - nt >= Target.Value Then '前批剩余大于本次领用
            Target.Offset(, 1).Value = arr(hs(minr), 2) '领用价格=前批价格
            Target.Offset(, 2).Value = Target.Offset(, 1).Value * Target.Value '领用金额=前批价格*本次领用数量
        Else '否则
            ssum = ssum + (smin - nt) * arr(hs(minr), 2) '领用金额为前批剩余金额之和
            tsum = Target.Value - (smin - nt) '本次领用数量为前批剩余数量
            For i = minr + 1 To maxr '
                If tsum > arr(hs(i), 1) Then '本次领用数量大于前批剩余数量
                    ssum = ssum + arr(hs(i), 1) * arr(hs(i), 2) '领用金额为前批剩余金额+不足数量*新价格
                    tsum = tsum - arr(hs(i), 1) '
                Else '否则
                    ssum = ssum + tsum * arr(hs(i), 2) '领用金额为领用数量*新价格
                End If
            Next
            Target.Offset(, 1).Value = ssum / Target.Value '10列的数据(领用价格)
            Target.Offset(, 2).Value = ssum '11列的数据(领用金额)
            End If
            Target.Offset(, 3).Resize(, 3).FormulaR1C1 = Array("=SUM(R5C6:RC[-6])-SUM(R5C9:RC[-3])", "=RC[1]/RC[-1]", "=SUM(R5C8:RC[-6])-SUM(R5C11:RC[-3])") '给12、13、14列写公式
    End If
    Application.EnableEvents = True
    Set d = Nothing
    Exit Sub
ll:
    Target.Value = "": Target.Resize(, 6).Value = "" '若目标值为空则从目标列处起后6列为空
     Application.EnableEvents = True
End Sub

TA的精华主题

TA的得分主题

 楼主| 发表于 2012-7-16 10:19 | 显示全部楼层
sctsg 发表于 2012-7-16 09:14
试试,A 列不为空就可自动计算

这是什么文件,打开方式用什么?请明示!

TA的精华主题

TA的得分主题

发表于 2012-7-16 15:19 | 显示全部楼层
[广告] VBA代码宝 - VBA编程加强工具 · VBA代码随查随用  · 内置多项VBA编程加强工具       ★ 免费下载 ★      ★使用手册
840205910 发表于 2012-7-16 10:14
老师,是不是这样理解?

Private Sub Worksheet_Change(ByVal Target As Range)

理解基本上正确了啊。
呵呵 不过我也不知道会不会中间哪里没考虑好,你最好找个已经做好的正确文件做一下测试。
您需要登录后才可以回帖 登录 | 免费注册

本版积分规则

手机版|关于我们|联系我们|ExcelHome

GMT+8, 2024-10-1 01:30 , Processed in 0.040676 second(s), 14 queries , Gzip On, MemCache On.

Powered by Discuz! X3.4

© 1999-2023 Wooffice Inc.

沪公网安备 31011702000001号 沪ICP备11019229号-2

本论坛言论纯属发表者个人意见,任何违反国家相关法律的言论,本站将协助国家相关部门追究发言者责任!     本站特聘法律顾问:李志群律师

快速回复 返回顶部 返回列表