Excel multi tiered lists in data validatation using alphanumeric fields - excel

I am using multi tiered lists and data validation and have an issue when the fields are alpha numeric
eg
Col 1 Col 2
100 Dairy 101 Milk
102 Cheese
200 Bakery 201 Bread
202 Cake
If you choose 100 Dairy in the drop down list Col1 Col2 will not give the 2 fields to choose from however if you remove one of the sets of numbers then data validation will provide the 2 options in col 2
In Column 2 Data validation I am using =Indirect(A1)
How can I have both Number and letters in both of my drop down lists
Any assistance appreciated

A Name (named range) cannot start with a digit or contain spaces. So, in your validation formula, you have to change your entry in column A into the actual name that is being used for your dependent dropdown.
If you used the Excel Create Name wizard, then something like:
=INDIRECT(SUBSTITUTE(" " & $A$1," ","_"))
That will only work if ALL of your dependent lists start with a digit. If not, you will need a different algorithm.
eg:
=INDIRECT(SUBSTITUTE(IF(ISNUMBER(-LEFT($A$1))," ","")&$A$1," ","_"))
If you made up your own names, again, you will need a different algorithm.

Related

Excel - SUBTOTAL but only where particular criteria is met (SUMIF/AVERAGEIF)

EDIT: The document is set up like a series of dashboards. Some if the data linked to the many graphs is in pivot tables and some just regular tables. Because there are so many graphs, I use some user selection buttons and fields to change what data is shown in these graphs.
Some users open the file in office 2016.
All solutions I found were either limited to 365 or involved creating new data tables or columns which I was trying to avoid as it would mean a fair bit of rework. I instead just used a set of nested IFS and will eventually look at changing these particular pivots to regular tables with index lookups to enable the actual data to be in multiple columns.
I currently use a SUBTOTAL function to either sum, count or average a bunch of cells in a range. I was previously manually filtering the range so I was only totaling the rows I wanted, however the need has arisen to be able to look at several criteria at once.
i.e in the example below, I was previously manually filtering range to only include "Apple" but now I need to be able to total "Apple", "Orange", "Banana" separately, at the same time.
The subtotal fields are used in graphs and I have a cell (F5) that houses a number corresponding to either SUM, COUNT or Average (9, 2 or 1) to use in the subtotal formulas in the "Summary table" which is linked to other functionality within the workbook and I need to still be able to retain that functionality.
Example of how my sheet is setup:
Raw Data
Product Type
Sales QTY
Date
Apple
4
1/9/21
Orange
3
6/9/21
Banana
2
10/9/21
Apple
6
14/9/21
Orange
6
20/9/21
Apple
5
29/9/21
The Criteria I want to match is in Column 1 (Product Type) of the summary table.
Basically, I then want to be able to end up with the ability to display the data either as Totals:
$F$5 = 9
for each line: SUBTOTAL($F$5,SalesQTY)
Summary Table
Product Type
Result (Sales Per Month)
Apple
15
Orange
9
Banana
2
Or as Averages:
$F$5 = 1
for each line: SUBTOTAL($F$5,SalesQTY)
Product Type
Result (Average QTY per Sale)
Apple
5
Orange
4.5
Banana
2
Or as a Count:
$F$5 = 2
for each line: SUBTOTAL($F$5,SalesQTY)
Product Type
Result (# Sales Transactions)
Apple
2
Orange
2
Banana
1
Is there some way I can combine SUMIF and also SUBTOTAL but also be able to retain the ability to flick between average, sum and count?
Here is a formula to create a dynamic summary table in excel 365. If you have any earlier version of excel, the formula would be different and rows would have to be manually added or removed. I'm assuming your table is called Data_Table.
=LET(
Column_Product, Data_Table[Product Type],
Column_QTY, Data_Table[Estimated],
Column_Date, Data_Table[Date]
Column_Key, Column_Product,
Column_Filter1, Column_QTY,
Column_Filter2, Column_Date,
List_Filter1, UNIQUE(Column_Product),
List_Filter2, 1,
Categories, SORT(UNIQUE(Column_Key)),
Array_BoolKey, (TRANSPOSE(Column_Key)=Categories)+0,
Mask1, TRANSPOSE(ISNUMBER(XMATCH(Column_Filter1,List_Filter1))),
Mask2, TRANSPOSE(Column_Filter2>List_Filter2),
Array_BoolMasked, Array_BoolKey*Mask1*Mask2,
Masked_QTY, IFERROR(Array_BoolMasked*TRANSPOSE(Column_QTY),0),
Masked_Date, IFERROR(Array_BoolMasked*TRANSPOSE(Column_Date),0),
Array_Ones, SEQUENCE(COLUMNS(Array_BoolMasked),1,1,0),
Months, DATEDIF(MIN(Column_Date),MAX(Column_Date),"M"),
Body_Count, MMULT(Array_BoolMasked, Array_Ones),
Body_Sum_QTY, MMULT(Masked_FtModeled, Array_Ones),
Body_Average_PerSale, Body_Sum_QTY/Body_Count,
Body_Sum_QTY_PerMo, MMULT(Masked_FtModeled, Array_Ones)/Months,
Total_Count, IFERROR(SUM(Body_Count_Lines),"-"),
Total_QTY_PerMo, IFERROR(SUM(Body_Sum_QTY)/Months,"-"),
Total_Average_PerSale, IFERROR(SUM(Body_Sum_QTY)/Total_Count,"-"),
Array_Seq, {1,2,3,4,5},
Array_Header, CHOOSE(Array_Seq, "Product Type", "Sales Per Month", "Average QTY per Sale", "# Sales Transactions"),
Array_Body, CHOOSE(Array_Seq, Categories, Body_Sum_QTY_PerMo, Body_Average_PerSale, Body_Count),
Array_Total, CHOOSE(Array_Seq, "Total", Total_QTY_PerMo, Total_Average_PerSale, Total_Count),
Range1,Array_Header,
Range2,Array_Body,
Range3,Array_Total,
Rows1,ROWS(Range1), Rows2,ROWS(Range2), Rows3,ROWS(Range3), Cols1,COLUMNS(Range1),
RowIndex, SEQUENCE(Rows1 + Rows2 + Rows3), ColIndex,SEQUENCE(1, Cols1),
RangeTable,IF(
RowIndex<=Rows1,
INDEX(Range1,RowIndex,ColIndex),
IF(RowIndex<=Rows1+Rows2,
INDEX(Range2,RowIndex-Rows1,ColIndex),
INDEX(Range3,RowIndex-Rows1-Rows2,ColIndex)
)),
Return, RangeTable,
Return
)
I wrote this generically so you could add filters for only certain products, or minimum quantity, or a date range, or other criteria. Above, I set up the filter to pass everything.
Solution Used:
To avoid having to rework the many other tables in the sheet that rely on this field and also as some user open this file with older (non-365) versions of excel, I opted for a series of nested IF (CountIF, SumIF, AverageIF) statements instead.

Excel sort function to "skip" 1st row

My question is because I wanted to sort the data as provided in the following question:
How to select all the column based minimum date value in a sheet
What I wanted to do is select the data (Range A1:F9) and sort it:
NAME
CARD NUMBER
ACCOUNT NUMBER
SBL Transaction Type
SBL Transaction Amount
SBL Transaction Date
B
4779
1
POS purchase
280
02-08-2021
B
4779
1
POS purchase
1
03-05-2021
S
1475
2
POS purchase
389
05-04-2021
S
1475
2
POS purchase
755
05-11-2021
S
1475
2
POS purchase
1794
05-15-2021
A
0173
3
POS purchase
1
02-01-2021
A
0173
3
POS purchase
1
02-02-2021
A
0173
3
POS purchase
1
02-03-2021
What I did is select the data including header =SORT(A1:F9,6) and which results in sorting the header along with the data (of course):
I then got the idea to have the SORT function to disregard the first row and then sort the rest.
My first attempt was =IF(ROW(A1:F9)=1,A1:F9,SORT(A1:F9,6))
As you can see the header worked fine, but the sorted data includes the header, since it's the last in range after sorting A1:F9.
Excluding the header row from the sort range =IF(ROW(A1:F9)=1,A1:F9,SORT(A2:F9,6)) also doesn't work, since the range is then smaller than the output range resulting in the following error and still skips one data line:
I managed to get it correct by inserting a substitute header of al zeroes to the sort range and than sort stack the sorted range onto the headers with this function (which also gives room for two row headers):
=LET(D,A1:F9,rowD,ROW(D),rowsD,ROWS(D),colsD,COLUMNS(D),H,A1:F1,header,INDEX(D,1,1):INDEX(D,ROWS(H),COLUMNS(H)),subsHeader,SEQUENCE(1,colsD,0,0),subsD,IF(rowD<=ROWS(header),subsHeader,D),sortedSubsD,SORT(subsD,6),IF(SEQUENCE(rowsD)<=ROWS(header),header,sortedSubsD))
But I wondered if there's a more elegant way using formula to sort a data range without affecting the header.
Result is =LET(data;A1:F9;header;A1:F2;sortCol;6;SORTBY(data;IF(ROW(data)>ROWS(header);1;0);1;INDEX(data;;sortCol);1)) thanks to Darren Bartrup-Cook's contribution.
If you have a spare column add a 0 next to the header and leave the other rows blank. You can then sort on that column first, followed by the other column.
You can then SORTBY column A and then column F.
=SORTBY(B1:F6,A1:A6,1,F1:F6,1)

Excel IF OR Statement

I am having trouble determining the correct way to calculate a final rank order for four categories. Each of the four metrics make up a higher group. A Top 10 of each category is applied to the respective product to risk analysis.
CURRENT LOGIC - Assignment of 25% max per category.
Columns - Y4
Parts
0.25
25
=IF(L9=1,$Y$4,IF(L9=2,$Y$4*0.9, IF(L9=3,$Y$4*0.8, IF(L9=4,$Y$4*0.7, IF(L9=5,$Y$4*0.6, IF(L9=6,$Y$4*0.5, IF(L9=7,$Y$4*0.4, IF(L9=8,$Y$4*0.3, IF(L9=9,$Y$4*0.2, IF(L9=10,$Y$4*0.1,0))))))))))
DESIRED...
I would like to use a statement to determine three criteria in order to apply a score (1=100, 2=90, 3=80, etc..).
SUM the rank positions of each of the four categories-apply product rank ascending (not including NULL since it's not in the Top 10)
IF a product is identified in more than one metric-apply a significant contribution weight of (*.75),
IF a product has the number 1 rank in any of the four metrics-apply a score of (100).
Data - UPDATED EXAMPLE
(Product) Parts Labor Overhead External Final Score
"XYZ" 3 1 7 7 100
"ABC" NULL 6 NULL 2 100
"LMN" 4 NULL NULL NULL 70
This is way beyond my capability. ANY assistance is appreciated greatly!!!
Jim
I figured this is a good start and I can alter the weight as needed to reflect the reality of the situation.
=AVERAGE(G28:I28)+SUM(G28:I28)*0.25
However, I couldn't figure out how to put a cap on the score of no more than 100 points.
I am still unclear of what exactly you are attempting and if this will work, but how about this simple matrix using an array formula and some conditional formatting.
Array Formula in F2 (make sure to press Ctrl+Shift+Enter when exiting formula edit mode)
=MIN(100,SUM(IF(B2:E2<>"NULL",CHOOSE(B2:E2,100,90,80,70,60,50,40,30,20,10))))
Conditional Formatting defined as shown below.
Red = 100 value where it comes from a 1
Yellow = 100 value where it comes from more than 1 factor, but without a 1.

List of records to assign to X number of people

I have list of records which I want to assign to three people (eg.) equally.
So for example with 15 records, to split to three people named XYZ, PQR and ABC:
Case Name
123 XYZ
124 XYZ
135 XYZ
138 ABC
145 ABC
167 ABC
258 PQR
259 PQR
260 PQR
Considering your Comment, if Case is in A1 and three people's names are in F2:F4 (ie in Column4) please try in B2 and copied down to suit:
=OFFSET(B$2,INT(ROW()-2)/COUNTA(F:F)-COUNTA(F:F)*INT((ROW()-2)/COUNTA(F:F)^2),4)
You have a list of Cases to be assigned “equally” over a pool of People.
However, the Cases can only be assigned “equally” is their number is an exact multiple of the number of People, otherwise the residual cases will be assigned as per the order in the list of people, i.e. if you have 31 cases to be distributed among 4 individuals, then three people will have 8 cases while the remaining one will receive 7.
Assuming the list of Cases (including header) is located at B6:B40 and the list of People (also with header) is at G6:G10, and blank records, if any, are at the end of each list. (These formulas will work with Cases coded as numeric or alpha)
To assign the cases one by one to each person enter the following FormulaArray in the range C7:C40
(Formulas Array are entered by pressing [Ctrl] + [Shift] + [Enter] together)
=IF($B$7:$B$40="","",INDEX($G$7:$G$10,
1+MOD(-1+COUNTA($G$7:$G$10)
+(1+ROW($B$7:$B$40)-ROW($B$7)),
COUNTA($G$7:$G$10))))
Fig. 1
To assign the cases using the pattern shown in the sample data we need first to add a field to the list of persons in order to calculate the distribution of the cases (this makes the formula to allocate people easier to read, maintain and shorter) . In cell H6 enter the field name Count then in range H7:H10 enter this FormulaArray:
=IF($G$7:$G$10="","",
INT(COUNTA($B$7:$B$40)/COUNTA($G$7:$G$10))
+((1+ROW($G$7:$G$10)-ROW($G$7))<=
MOD(COUNTA($B$7:$B$40),COUNTA($G$7:$G$10)))*1)
Fig. 2
Then enter this `FormulaArray` in `E7` and copy to the end of the range.
=IFERROR(IF($B7="","",
IF(COUNTIF($G$7:$G$10,$E6)=0,
INDEX($G$7:$G$10,MATCH(0,COUNTIF(E$6:E6,$G$7:$G$10),0)*1),
IF(COUNTIF($E$6:$E6,$E6)<INDEX($H$7:$H$10,MATCH($E6,$G$7:$G$10,0)),$E6,
INDEX($G$7:$G$10,MATCH(0,COUNTIF(E$6:E6,$G$7:$G$10),0)*1)))),"")
Fig. 3

Find the top n values in a range while keeping the sum of values in another range under x value

I'd like to accomplish the following task. There are three columns of data. Column A represents price, where the sum needs to be kept under $100,000. Column B represents a value. Column C represents a name tied to columns A & B.
Out of >100 rows of data, I need to find the highest 8 values in column B while keeping the sum of the prices in column A under $100,000. And then return the 8 names from column C.
Can this be accomplished?
EDIT:
I attempted the Solver solution w/ no luck. 200 rows looks to be the max w/ Solver, and that is what I'm using now. Here are the steps I've taken:
Create a column called rank RANK(B2,$B$2:$B$200) (used column D -- what is the purpose of this?)
Create a column called flag just put in zeroes (used column E)
Create 3 total cells total_price (=SUM(A2:A200)), total_value (=SUM(B2:B200)) and total_flag (=(E2:E200))
Use solver to minimize total_value (shouldn't this be maximize??)
Add constraints -Total_price<=100000 -Total_flag=8 -Flag cells are binary
Using Simplex LP, it simply changes the flags for the first 8 values. However, the total price for the first 8 values is >$100,000 ($140k). I've tried changing some options in the Solver Parameters as well as using different solving methods to no avail. I'd like to post an image of the parameter settings, but don't have enough "reputation".
EDIT #2:
The first 5 rows looks like this, price goes down to ~$6k at the bottom of the table.
Price Value Name Rank Flag
$22,538 42.81905675 Blow, Joe 1 0
$22,427 37.36240932 Doe, Jane 2 0
$17,158 34.12127693 Hall, Cliff 3 0
$16,625 33.97654031 Povich, John 4 0
$15,631 33.58212402 Cow, Holy 5 0
I'll give you the solver solution as a starting point. It involves the creation of some extra columns and total cells. Note solver is limited in the amount of cells it can handle but will work with 100 anyway.
Create a column called rank RANK(B2,$B$2:$B$100)
Create a column called flag just put in zeroes
Create 3 total cells total_price, total_value and total_flag
Use solver to minimize total_value
Add constraints
-Total_price<=100000
-Total_flag=8
-Flag cells are binary
This will flag the rows you want and you can grab the names however you want.

Resources