Parsing an excel sheet with VBA - arrays
Scenario: In my worksheet I have data in multiple columns on the following format (this is an ASCII generated table to facilitate visualization, the symbols are not on the original spreadsheet):
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| Count | Indentifier1 | Identifier2 | Identifier3 | ProductName | Location | Type | Status | RegistryDate |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 1 | azjzjzj3611a | | | Super electric board - high load | SEA | General | Sold out -- Used -- | 4/17/2019 4:19 |
| | | | | | | | Good | |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 2 | y000zj9y30 | | | electric board - low battery | SEA | General | Sold out -- Used -- Good | 5/12/2015 3:48 |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 3 | | | | Super jet-ski 01 Special | SHORE | TEST - Utility - Vehicle | | |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 4 | a30y970y3 | | | Super jet-ski 01 Special | SHORE | TEST - Utility - Vehicle | Used - Good | |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 5 | | | | Ball 10-Type1 | BEACH | TEST - Utility - Small-Item | | |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 6 | azjzjzja9zjy9 | | | Ball 10-Type1 | BEACH | | | |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 7 | azjzjzja9zjy9 | | | Ball 10-Type1 | BEACH | TEST - Utility - Small-Item | Sold out -- Used - Good | 6/10/2013 0:00 |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 8 | a3044aa69 | 1007750 | | Ball 10-Type1 | | | | |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 9 | | | | Ball 10-Type1 | BEACH | TEST - Utility - Small Unit | | |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 10 | a3044aa69 | | BLL101 | Ball 10-Type1 | BEACH | TEST - Utility - Small Unit | Used - Good | |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 11 | a3044aa69 | 1007750 | BLL101 | BALL 10-TYPE1 | Beach | TEST - Utility | | |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 12 | y0003aa67 | 36021 | | Ball 5-Type1 | | | | |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 13 | | | | Ball 5-Type1 | RIDGE | Group - Special | | |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 14 | y0003aa67 | | | Ball 5-Type1 | RIDGE | | | |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 15 | y0003aa67 | | BLL051 | Ball 5-Type1 | RIDGE | Group - Special | Used - Good | |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
| 16 | y0003aa67 | 36021 | BLL051 | BALL 5-TYPE1 | Ridge | Group - Special | | |
+-------+---------------+-------------+-------------+----------------------------------+----------+-----------------------------+--------------------------+----------------+
Obs.: As per the table, the data can have multiple entries, where different information is displayed in each column. The differences may be either the format (upper/lower-case) or content (has data or not).
Objective: I am trying to retrieve the information from this table, without loosing data. Ex: If two rows have the same data, but one is lower case whereas the other is upper case, either could be retrieved (no preference), but if there is different data (maybe there is a slight difference in the item name or status), I am trying to retrieve all the data.
Done so far: I was able to simple create an array, loop it, and compare the data manually, but the result is sub-optimal, since it just aggregates the data in the same cell where it is different. Which would still require manual checking/cleaning.
Obs2.: This table has around 22 thousand rows.
Obs3.: Another issue of this data-set is that none of the columns is completely filled. Sometimes I have data for all identifiers and item name, sometimes an identifier is missing, sometimes the name is missing, and sometimes just one identifier is available (no name or anything else).
Question: Is there a way to do this?
Wanted output:
+-------+--------------+-------------+-------------+------------------------------+----------+-----------------------------+--------------------------+----------------+
| Count | Indentifier1 | Identifier2 | Identifier3 | ProductName | Location | Type | Status | RegistryDate |
+-------+--------------+-------------+-------------+------------------------------+----------+-----------------------------+--------------------------+----------------+
| 1 | azjzjzj3611a | | | Super electric | SEA | General | Sold out -- Used -- | 4/17/2019 4:19 |
| | | | | board - high load | | | Good | |
+-------+--------------+-------------+-------------+------------------------------+----------+-----------------------------+--------------------------+----------------+
| 2 | y000zj9y30 | | | electric board - low battery | SEA | General | Sold out -- Used -- Good | 5/12/2015 3:48 |
+-------+--------------+-------------+-------------+------------------------------+----------+-----------------------------+--------------------------+----------------+
| 3 | a30y970y3 | | | Super jet-ski 01 Special | SHORE | TEST - Utility - Vehicle | Used - Good | |
+-------+--------------+-------------+-------------+------------------------------+----------+-----------------------------+--------------------------+----------------+
| 4 | a3044aa69 | 1007750 | | Ball 10-Type2 | BEACH | TEST - Utility - Small-Item | Sold out -- Used - Good | 6/10/2013 0:00 |
+-------+--------------+-------------+-------------+------------------------------+----------+-----------------------------+--------------------------+----------------+
| 5 | a3044aa69 | 1007750 | BLL101 | Ball 10-Type1 | BEACH | TEST - Utility - Small Unit | Used - Good | |
+-------+--------------+-------------+-------------+------------------------------+----------+-----------------------------+--------------------------+----------------+
| 6 | y0003aa67 | 36021 | BLL051 | BALL 5-TYPE1 | Ridge | Group - Special | Used - Good | |
+-------+--------------+-------------+-------------+------------------------------+----------+-----------------------------+--------------------------+----------------+
Code for array approach:
Sub cleanup_detail()
Dim raw_array As Variant
Dim w As Workbook
Dim loopvar1 As Long
Set w = ThisWorkbook
raw_array = w.Worksheets("Sheet1").UsedRange
For loopvar1 = 2 To UBound(raw_array, 1)
If raw_array(loopvar1 + 1, 2) = "" Or raw_array(loopvar1 + 1, 2) = "0" Then
If raw_array(loopvar1 + 1, 3) = "" Or raw_array(loopvar1 + 1, 3) = "0" Then
If raw_array(loopvar1 + 1, 4) = "" Or raw_array(loopvar1 + 1, 4) = "0" Then
If raw_array(loopvar1 + 1, 5) = "" Or raw_array(loopvar1 + 1, 5) = "0" Then
Next loopvar1
ElseIf raw_array(loopvar1 + 1, 5) = raw_array(loopvar1, 5) Then
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 2) = raw_array(loopvar1 + 1, 2) & "/" & raw_array(loopvar1, 2)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 3) & "/" & raw_array(loopvar1, 3)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 4) & "/" & raw_array(loopvar1, 4)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 5)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 6) & "/" & raw_array(loopvar1, 6)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 7) & "/" & raw_array(loopvar1, 7)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 8) & "/" & raw_array(loopvar1, 8)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 9) & "/" & raw_array(loopvar1, 9)
End If
ElseIf raw_array(loopvar1 + 1, 4) = raw_array(loopvar1, 4) Then
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 2) = raw_array(loopvar1 + 1, 2) & "/" & raw_array(loopvar1, 2)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 3) & "/" & raw_array(loopvar1, 3)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 4)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 5) & "/" & raw_array(loopvar1, 5)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 6) & "/" & raw_array(loopvar1, 6)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 7) & "/" & raw_array(loopvar1, 7)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 8) & "/" & raw_array(loopvar1, 8)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 9) & "/" & raw_array(loopvar1, 9)
End If
ElseIf raw_array(loopvar1 + 1, 3) = raw_array(loopvar1, 3) Then
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 2) = raw_array(loopvar1 + 1, 2) & "/" & raw_array(loopvar1, 2)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 3) & "/" & raw_array(loopvar1, 3)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 4) & "/" & raw_array(loopvar1, 4)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 5) & "/" & raw_array(loopvar1, 5)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 6) & "/" & raw_array(loopvar1, 6)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 7) & "/" & raw_array(loopvar1, 7)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 8) & "/" & raw_array(loopvar1, 8)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 9) & "/" & raw_array(loopvar1, 9)
End If
ElseIf raw_array(loopvar1 + 1, 2) = raw_array(loopvar1, 2) Then
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 2) = raw_array(loopvar1 + 1, 2)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 3) & "/" & raw_array(loopvar1, 3)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 4) & "/" & raw_array(loopvar1, 4)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 5) & "/" & raw_array(loopvar1, 5)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 6) & "/" & raw_array(loopvar1, 6)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 7) & "/" & raw_array(loopvar1, 7)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 8) & "/" & raw_array(loopvar1, 8)
w.Worksheets("Sheet1").Cells(loopvar1 + 1, 3) = raw_array(loopvar1 + 1, 9) & "/" & raw_array(loopvar1, 9)
End If
Next loopvar1
End Sub
Related
Print tic tac toe board fortran90
I am just trying to create a subroutine to print out the current state of the board in tic tac toe. Zeros are blank spaces, 1's are X's, and 2's are O's. I'm not sure what's wrong with my code, but ti would print out the current state, instead it prints out a bunch of different, incorrect boards. Any help at all would be greatly appreciated. !!!!!!!!!This is my code and subroutine: program ttt implicit none integer, dimension(9) :: board integer :: playerx character (len=1), dimension(9) :: cboard integer :: i, j !Print board with numbered spots !print *, "Enter a number 1-9 to play tic-tac-toe" print *, " " print "(a11)", " 1 | 2 | 3 " print "(a11)", "---+---+---" print "(a11)", " 4 | 5 | 6 " print "(a11)", "---+---+---" print "(a11)", " 7 | 8 | 9 " print *, " " board = (/ 2, 0, 0, & 0, 1, 0, & 0, 0, 1 /) playerx = 1 call printboard(board, playerx) end program ttt ! Subroutine to print out the current state of the board subroutine printboard(board, playerx) implicit none integer, intent(in), dimension(9) :: board integer, intent(in) :: playerx character (len=1), dimension(9) :: cboard integer :: i, j ! board array is series of 1s, 2s, and 0s. set 1 = x, 2 = o, and 0 = " " if (playerx == 1) then do i = 1,9 do j = 1, 9 if (board(i) == 0) cboard(j) = " " if (board(i) == 1) cboard(j) = "x" if (board(i) == 2) cboard(j) = "o" if (j < 0 .and. j < 4) then print "(a1, a1, a3, a1, a3, a1)", " ", cboard(j), " | ", cboard(j), " | ", cboard (j) print "(a11)", "---+---+---" endif if (j > 3 .and. j < 7) then print "(a1, a1, a3, a1, a3, a1)", " ", cboard(j), " | ", cboard(j), " | ", cboard (j) print "(a11)", "---+---+---" endif if (j > 6 .and. j < 10) then print "(a1, a1, a3, a1, a3, a1)", " ", cboard(j), " | ", cboard(j), " | ", cboard (j) print "(a11)", " " endif endif end subroutine printboard This is what the code produces: 1 | 2 | 3 ---+---+--- 4 | 5 | 6 ---+---+--- 7 | 8 | 9 o | o | o ---+---+--- o | o | o ---+---+--- o | o | o ---+---+--- o | o | o o | o | o o | o | o | | ---+---+--- | | ---+---+--- | | ---+---+--- | | | | | | | | ---+---+--- | | ---+---+--- | | ---+---+--- | | | | | | | | ---+---+--- | | ---+---+--- | | ---+---+--- | | | | | | x | x | x ---+---+--- x | x | x ---+---+--- x | x | x ---+---+--- x | x | x x | x | x x | x | x | | ---+---+--- | | ---+---+--- | | ---+---+--- | | | | | | | | ---+---+--- | | ---+---+--- | | ---+---+--- | | | | | | | | ---+---+--- | | ---+---+--- | | ---+---+--- | | | | | | x | x | x ---+---+--- x | x | x ---+---+--- x | x | x ---+---+--- x | x | x x | x | x x | x | x
Your code seems to be a little bit complicated. I would have it simplified here and there. First of all, you can use 2D array to store your data. I think it would be way more natural. Instead of filling character(1), dimension(3,3) :: cboard based on values from integer, dimension(3,3) :: board you can simply introduce function that will provide required character depending on the value stored inside your board. When it comes to printing, I think that putting multiple print sections, that behave differently (depending on whether there will be a new line or not), is an overkill. It is also a good idea to put parts of the code (that are responsible for a certain logic of your application) into modules. This way, you can reuse and replace them. E.g. you can easily add new module that will print your board differently. When it comes to Fortran, it's a good idea to remember column/row order in arrays. Might be confusing for people coming with the experience based on different languages. module board_printer implicit none contains function integer2char(x) integer, intent(in) :: x character(1) :: integer2char if(x == 0) then integer2char = ' ' else if(x == 1) then integer2char = 'x' else integer2char = 'o' end if end function integer2char subroutine printboard(board) integer, intent(in), dimension(3, 3) :: board integer :: i do i = 1, 3 write(*, fmt="(a)") ' '//integer2char(board(i,1))//' | '//integer2char(board(i,2))//' | '//integer2char(board(i,3))//' ' if( i /= 3) then write(*, fmt="(a)") '---+---+---' end if end do write(*,*) "" end subroutine printboard end module board_printer program ttt use board_printer implicit none integer, dimension(3, 3) :: board write(*,fmt="(a)") "Enter a number 1-9 to play tic-tac-toe" write(*,fmt="(a)") " " write(*,fmt="(a)") ' 1 | 4 | 7 ' write(*,fmt="(a)") '---+---+---' write(*,fmt="(a)") ' 2 | 5 | 8 ' write(*,fmt="(a)") '---+---+---' write(*,fmt="(a)") ' 3 | 6 | 9 ' write(*,fmt="(a)") '' board = reshape((/ 0, 0, 0, 0, 0, 0, 0, 0, 0 /), shape(board) ) call printboard(board) board = reshape((/ 1, 0, 0, 0, 1, 0, 0, 0, 1 /), shape(board) ) call printboard(board) board = reshape((/ 0, 0, 1, 0, 1, 0, 1, 0, 0 /), shape(board) ) call printboard(board) board = reshape((/ 2, 0, 0, 0, 2, 0, 0, 0, 2 /), shape(board) ) call printboard(board) board = reshape((/ 1, 0, 2, 0, 1, 0, 2, 0, 1 /), shape(board) ) call printboard(board) end program ttt
Flatten table in Excel using VBA
I'm looking to use VBA to transform a raw data extract into a flattened table for querying. Currently, I have a raw data table in Excel that summarizes the status of Phases A, B, and C for a given Engagement (note: some Engagements may not have data for all 3 phases). Row| EngagementID | A_date | A_status | B_date | B_status | C_date | C_status 1 | 201 | 2/2 | Approved | | | | 2 | 201 | | | 3/5 | Approved | | 3 | 201 | | | | | 4/1 | Pending 4 | 203 | 2/12 | Submitted| | | | 5 | 203 | | | 2/20 | Approved | | 6 | 207 | 2/5 | Approved | | | | I need to flatten the table to look like something this: Row| EngagementID | Date | Status 1 | 201 | 2/2 | Approved 2 | 201 | 3/5 | Approved 3 | 201 | 4/1 | Pending 4 | 203 | 2/12| Submitted 5 | 203 | 2/20| Approved 6 | 207 | 2/5 | Approved Additionally, I'd like to add a column for the Phase so that I can "tag" each row with the Phase (A, B, or C) that it is associated with. I've tried the following VBA code, but it flattens the table vertically, as opposed to horizontally (merging 3 rows into 1, as opposed to 3 columns into 1): Private Sub test() Dim R As Long Dim i As Integer i = 1 R = 2 Count = 0 Do While Not IsEmpty(Range("A" & R)) If Cells(R, 1).Value = Cells(R + 1, 1).Value Then Count = Count + 1 Else i = 1 Do While i <= Count Cells(R - Count, 2 + (2 * i)).Value = Cells(R - Count + i, 2 + (2 * i)) Cells(R - Count, 3 + (2 * i)).Value = Cells(R - Count + i, 3 + (2 * i)) i = i + 1 Loop i = 1 Do While i <= Count Rows(R - Count + i).Delete i = i + 1 R = R - 1 Loop Count = 0 End If R = R + 1 Loop End Sub Please help!!
Try this code Sub Test() Dim a As Variant Dim b As Variant Dim i As Long Dim j As Long Dim k As Long a = Range("A1").CurrentRegion.Value ReDim b(1 To UBound(a, 1) * 3, 1 To 3) For i = 2 To UBound(a, 1) For j = 2 To UBound(a, 2) Step 2 If a(i, j) <> "" And a(i, j + 1) <> "" Then k = k + 1 b(k, 1) = a(i, 1) b(k, 2) = a(i, j) b(k, 3) = a(i, j + 1) End If Next j Next i Range("J1").Resize(k, UBound(b, 2)).Value = b End Sub
Replace Square-Expression in Maple
Given a maple expression like f := (y + 5)^2 + x^2 How can I replace all occurrences of the square function with a custom function? The result I want to have would be square(y + 5) + square(x) I tried something like subs({x^2 = square(x)}, f) However, that only replaces the x^2 expression. I could of course list explicitly the (y + 5) term as well, but I want to replace any occurrence of (.)^2 without listing everything explicitly. How can I do this in Maple?
You can accomplish this using either subsindets or applyrule. expression:=(y-5)^2+3+sin(((z-1/3)^2/(t-(y-s)^2)))+F(f(17+p^2)^2); / 2 \ | / 1\ | | |z - -| | / 2\ 2 | \ 3/ | | / 2 \ | expression := (y - 5) + 3 + sin|------------| + F\f\p + 17/ / | 2| \t - (y - s) / applyrule(_a::anything^2=square(_a), expression); / / 1\ \ | square|z - -| | | \ 3/ | square(y - 5) + 3 + sin|-----------------| + F(square(f(square(p) + 17))) \t - square(y - s)/ subsindets(expression, '`^`'(anything,2), u->square(op(1,u))); / / 1\ \ | square|z - -| | | \ 3/ | square(y - 5) + 3 + sin|-----------------| + F(square(f(square(p) + 17))) \t - square(y - s)/
Detecting XOR in Karnaugh Maps
I got the following Karnaugh Maps but I am still having problems working out the expression for XOR from each table. Table 1 ------- WZ 00 01 11 10 ----------------------- 00 | | | | 1 | ----------------------- 01 | 1 | | | | ----------------------- XY 11 | | | | 1 | ----------------------- 10 | 1 | | | | ----------------------- Table 2 ------- WZ 00 01 11 10 ----------------------- 00 | | 1 | | | ----------------------- 01 | | | 1 | | ----------------------- XY 11 | | 1 | | | ----------------------- 10 | | | 1 | | ----------------------- It is XORs, but how can I easily deduce the XOR expressions?
I would not dismiss the variable z from the expression, because I think, the expression ¬z·(¬x·y·¬w + ¬x·w·¬y + ¬y·¬w·x + w·y·x) is not equal to (¬x·y·¬w + ¬x·w·¬y + ¬y·¬w·x + w·y·x). That would mean, that the K-map contains four doubles of ones, but there is only four singles. I would rather find the expression in the K-map and then use the laws of Boolean algebra. For the first table: ¬x·¬y·w·¬z + ¬x·y·¬w·¬z + x·y·w·¬z + x·¬y·¬w·¬z ¬z·((¬x + ¬y + w)·(¬x + y + ¬w)·(x + y + w)·(x + ¬y + ¬w)) //distributivity ¬z· (¬x + ¬y + w)·(¬x + y + ¬w)·(x + y + w)·(x + ¬y + ¬w) //relaxed syntax ¬z· (¬x·¬x + ¬x·y + ¬x·¬w + ¬y·¬x + ¬y·y + ¬y·¬w + w·¬x + w·y + w·¬w)· (x·x + x·¬y + x·¬w + y·x + y·¬y + y·¬w + w·x + w·¬y + w·¬w) //distributivity Because of the laws of idempotence (e.g.: ¬x·¬x=¬x), absorption (e.g.:¬x + ¬x·y=¬x) and complementation (e.g.: ¬x·x=0) the expression is equivalent to: ¬z· (¬x + 0 + ¬y·¬w + w·y + 0)· ( x + + 0 + y·¬w + + w·¬y + 0 ) ¬z· (¬x + ¬y·¬w + w·y)·(x + y·¬w + w·¬y) //just formatted ¬z· (¬x·x + ¬x·y·¬w + ¬x·w·¬y + ¬y·¬w·x + ¬y·¬w·y·¬w + ¬y·¬w·w·¬y + w·y·x + w·y·y·¬w + w·y·w·¬y) //distributivity ¬z· ( 0 + ¬x·y·¬w + ¬x·w·¬y + ¬y·¬w·x + 0 + 0 + w·y·x + 0 + 0 ) //using the three laws↑ again ¬z· (¬x·y·¬w + ¬x·w·¬y + ¬y·¬w·x + w·y·x) //how the 3-input XOR is defined ¬z· (x xor y xor w) For the second table: ¬x·¬y·¬w·z + ¬x·y·w·z + x·y·¬w·z + x·¬y·w·z z·((¬x + ¬y + ¬w)·(¬x + y + w)·(x + y + ¬w)·(x + ¬y + w)) //distributivity z· (¬x + ¬y + ¬w)·(¬x + y + w)·(x + y + ¬w)·(x + ¬y + w) //relaxed syntax z· (¬x·¬x + ¬x·y + ¬x·w + ¬y·¬x + ¬y·y + ¬y·w + ¬w·¬x + ¬w·y + ¬w·w)· (x·x + x·¬y + x·w + y·x + y·¬y + y·w + ¬w·x + ¬w·¬y + ¬w·w) //distributivity z· ( ¬x + + 0 + ¬y·w + + ¬w·y + 0 )· ( x + + 0 + y·w + + ¬w·¬y + 0 ) z· (¬x + ¬y·w + ¬w·y)·(x + y·w + ¬w·¬y) //just formatted z· (¬x·x + ¬x·y·w + ¬x·¬w·¬y + ¬y·w·x + ¬y·w·y·w + ¬y·w·¬w·¬y + ¬w·y·x + ¬w·y·y·w + ¬w·y·¬w·¬y) //distributivity z· ( 0 + ¬x·y·w + ¬x·¬w·¬y + ¬y·w·x + 0 + 0 + ¬w·y·x + 0 + 0) //using the three laws↑ again z· (¬x·y·w + ¬x·¬w·¬y + ¬y·w·x + ¬w·y·x) //how the 3-input XNOR is defined z· (x xnor y xnor w)
The first table contains an Xor expression : `First table` w \ wz ___________ xy \-----------------------+ | | | | 1 | +-----+-----+-----+-----+ | 1 | | | | | +-----+-----+-----+-----+ | y | | | | | 1 | | x | +-----+-----+-----+-----+ | | 1 | | | | +-----------------------+ ___________ z as you could see the middle of the table (Z area) is fake. that is, the table function is : F(Table1) = w'x'yz' + wx'y'z' + w'xy'z' + wxyz' in binary form you could see a zero column : F(Table) = 0010 eliminating Z F(xor)= 001 0100 ---------------\ 010 1110 ---------------/ 111 1000 100 ^--> fake and the final table must be something like this : `simplified xor table` w \ w 0 __1__ xy \-----------+ 00 | | 1 | +-----+-----+ 01 | 1 | | | +-----+-----+ | y And " F = wy' + w'y " is an Xor only |10 | 1 | | | between 2 variables, right? x | +-----+-----+ |11 | | 1 | +-----------+ The second table just contains an Xnor expression of the first one : `Second Table` F(Table2) = w'xyz + wxy'z + w'x'y'z + wx'yz w \ wz ___________ xy \-----------------------+ negation of table 2 is table 1 and vise versa | | 1 | | | F(Table2) = 1101 F(Table2)'= F(Table1) = 0010 +-----+-----+-----+-----+ 1011 0100 | | | 1 | | | 0001 1110 +-----+-----+-----+-----+ | y 0111 1000 | | | 1 | | | | ^--> fake ^ x | +-----+-----+-----+-----+ | | | | 1 | | +-----------------------+ ^ ___________ ^ ^ z ^ ^ ^ ^--------z'-------^ the final table is: w \ w 0 __1__ xy \-----------+ 00 | 1 | | +-----+-----+ 01 | | 1 | | +-----+-----+ | y And " F = w'y' + wy " is an Xnor |10 | | 1 | | x | +-----+-----+ |11 | 1 | | +-----------+ Always remember the tables that contain the zigzag pattern are either an Xor or Xnor expression.
Just put a copy of this map on the right hand side of it (or left, no difference) and then choose two tilted cubes. Now, we write the simplified function for both of them: (A = 1) (AND) (B=0 when C=1 and B=1 when C=0) (OR) (A = 0) (AND) (B=0 when C=0 and B=1 when C=1) that finaly gives this: (A AND (B XOR C)) OR (¬A AND (B XNOR C))
Basic rule for xor is that it gives 1 when odd number of input are 1. So in KMAP just see if 1 is present in all the odd number of 1's. Like WXYZ ( 0010, 1110 etc) if all gives 1 than there is a XOR in kmap.
VBA Array Manipulation
I found a macro (courtesy of Jerry Beaucaire) that splits up one worksheet into many based on unique values in a given column. This works great. However... The client has supplied a differently formatted worksheet which needs some gentle massaging to get into the format we need. First, let me show you a snippet of JB's code: MyArr = Application.WorksheetFunction.Transpose _ (ws.Columns(iCol).SpecialCells(xlCellTypeConstants)) From what I can tell (and I'm a total VB newbie, so what do I know..??), this populates an array with the selected row values And this: For Itm = 2 To UBound(MyArr) ...(code removed) ws.Range("A" & TitleRow & ":A" & LR).EntireRow.Copy _ Sheets(MyArr(Itm) & "").Range("A1") ...(code removed) Next Itm ...seems to do the copying. Alright. ...fine so far. The problem is that I need to add a step to the process. This will be tricky to explain. Please bear with me... Title row is row 1 Data starts in row 2 Each row has 9 columns: colA: identifier colB-colD: x,y,z values (for top of item) colE-colG: x,y,z values (for bottom of item) colH and colI: can be ignored These x,y and z values are used to define points that are used to plot lines in a 3D modelling program. Each row in the worksheet actually defines a line (well... a start point and an end point - "top" and "bottom") Unfortunately, the data(worksheet) we have received defines two sets of data for each line - both having the same start point, but with different end points. Put another way, starting with rows 3 and 4, the data in columns B-D is the same for both rows. This applies to rows 5 & 6, 7 & 8, etc. Since all we need are a set of data POINTS, we can safely use the values from cols E-G. HOWEVER... and this is where I need help... We need the first row of the newly created worksheet to start with the values from row 2, cols B-D. (ie. we can use the end points as our coordinates, but we still need the first start point) All the rest is fine the way it is. For example: Source Data: | A | B | C | D | E | F | G | 1 | id | x-top | y-top | z-top | x-bottom | y-bottom | z-bottom | 2 | H1 | 101.2 | 0.525 | 54.25 | 110.25 | 0.625 | 56.75 | 3 | H1 | 110.25| 0.625 | 56.75 | 121.35 | 2.125 | 62.65 | 4 | H1 | 110.25| 0.625 | 56.75 | 134.85 | 3.725 | 64.125 | B,C,D same as row 3 5 | H1 | 134.85| 3.725 | 64.125| 141.25 | 4.225 | 66.75 | 6 | H1 | 134.85| 3.725 | 64.125| 148.85 | 5.355 | 69.85 | B,C,D same as row 5 What I need: | A | B | C | D | E | F | G | 1 | id | x-top | y-top | z-top | x-bottom | y-bottom | z-bottom | 2 | H1 | | | | 101.2 | 0.525 | 54.25 | 3 | H1 | 101.2 | 0.525 | 54.25 | 110.25 | 0.625 | 56.75 | 4 | H1 | 110.25| 0.625 | 56.75 | 121.35 | 2.125 | 62.65 | 5 | H1 | 110.25| 0.625 | 56.75 | 134.85 | 3.725 | 64.125 | 6 | H1 | 134.85| 3.725 | 64.125| 141.25 | 4.225 | 66.75 | 7 | H1 | 134.85| 3.725 | 64.125| 148.85 | 5.355 | 69.85 | So... What's the best way to do this? Can I add to the existing macro to perform this operation? If so, better to modify the array? ...better to modify the Copy routine? ...and how?? Thanks in advance for your help and please don't suggest doing it manually. There are 70,000+ rows to parse! If you need more info, let me know!
The full macro is available for free to all at this location To achieve your connecting points, these additions should do it: For Itm = 2 To UBound(MyArr) ...(code removed) ws.Range("A" & TitleRow & ":A" & LR).EntireRow.Copy _ Sheets(MyArr(Itm) & "").Range("A1") Sheets(MyArr(Itm) & "").Rows(2).Insert xlShiftDown Sheets(MyArr(Itm) & "").Range("E2").Resize(, 3).Value = Sheets(MyArr(Itm) & "").Range("B3").Resize(, 3).Value ...(code removed) Next Itm