How can I make a blacklist in netlogo? - netlogo

I want to know how I can code the concept like blacklist?
I have 150 customers and 3 providers. all customers have this possibility to choose between providers based on specific rules. The model should run for 5 years and each year customers evaluate their provider and if it is not desirable, customers should change their providers. For the next years, customers choose between the remaining providers (the last provider now should be in blacklist just for 1 year) based on the same rule. The provider which is blocked by the customer just remains on the blacklist for 1 years.
Note. For example, customer 1 chooses provider 1 for the first years. At the end of the first year, customer evaluates the provider 1 and decide to change the provider. Now for the second year, the customer can choose just between provider 2 and 3. Then assume that for the second year, the customer selected provider 2 and at the end of the second year again wanted to change the provider. Then the customer can choose between provider 1 and 3 for the third year.

I believe that you want each customer to maintain its own blacklist rather than have a single blacklist that is available to all customers. If that is correct, then you need to create a turtles-own attribute for customers that contains their blacklist.
That blacklist is easiest to use if it is an agentset. That way, you can use not member? to exclude the providers when choosing. However, you will need to store it as a list of agents (never use identifiers like the who number) if you need more complex operations like remembering the order that they were added to the blacklist.
This code creates a blacklist, excludes the members from the selection, and adds and deletes from the blacklist probabilistically.
breed [providers provider]
breed [customers customer]
customers-own [blacklist]
to setup
clear-all
create-providers 3 [setxy random-xcor random-ycor set color red]
create-customers 10
[ setxy random-xcor random-ycor
set color blue
set blacklist (turtle-set [])
]
reset-ticks
end
to go
ask customers
[ let choice ifelse-value any? blacklist
[ one-of providers with [not member? self [blacklist] of myself] ]
[ one-of providers ]
; stuff here about purchasing from their choice
ask blacklist [ if random-float 1 < 0.3 [ die ] ]
if random-float 1 < 0.2 [ set blacklist (turtle-set blacklist choice) ]
show blacklist
]
tick
end

I believe you can use a list for each customer (as an attribute) for that. For example, if you have p providers (and you give them an id from 0 to p-1), then you star with set blacklist n-values p [-1]. When a provider with id = n goes to the list, you make its value zero: replace-item n blacklist 0.
Each year, you ask customers to increase the values of their blacklist that are >= 0. Like,
foreach blacklist [ provider_id ->
if provider_id >= 0 [
replace-item n blacklist (item provider_id blacklist + 1)
]
]
Finally, you replace-item n blacklist -1 if ever the provider n gets out of the blacklist!
Hope this helps. If you have any doubt, please ask!

Related

Sort list based on items' attribute and pick the first item

I want to sort a list of turtle's item sorted by decreasing attribute (from the highest value to the lowest), pick the item with the highest value (the first item of the sorted list; it may be not added recently but in previous step), and add it to the top of list.
I am doing
ask one-of agents [
let sorted_list sort-on [values] items
]
to sort the items in the list. values is defined in the range [0,1].
However, I do not know how to pick the item with the highest value and add it on the top of the list.
Furthermore, how can an agent remember which item he already picked from the list in order to not select the same twice (if the agent is selected again)?
I hope you can help me with this.
To sort a set of items in decreasing order by value, you need a minus sign as in:
ask one-of agents [
let sorted_list sort-on [(- values)] items
let best-choice first sorted_list
]
Or you could just sort in ascending order, and choose the last item instead of the first.
ask one-of agents [
let sorted_list sort-on [ values] items
let best-choice last sorted_list
]
I do not understand what you mean by "top".
add it on the top of the list.
I think maybe you mean that there is a different list of items, say "item-list", and you want to push the best-choice onto the front of this list. You could do this:
set item-list fput best-choice item-list
Furthermore, how can an agent remember which item he already picked
from the list in order to not select the same twice (if the agent is
selected again)?
Just give the agent a variable, most-recent-choice, and set that to
best-choice as soon as you select it. Or if you want to recall every
item the agent ever selected, give them a variable all-my-choices, and
keep a list in there. Initialize it to [] and fput best-choice onto it
at the time you select best-choice.
Good luck -- the problem you and Val are both working on seems to be a very complicated problem!

Tableau Calculation - String

I want output which consists of the count of familycode and output should be like below
so baically i need three category first will be single and multiple only ASK product count . 2nd will be Single ASK and single NON ask count and third one WIth only SIngle ASK ..... and ignore the other - categroy such as multiple NON ASK and ASK and NON ASK mIX.

Looking for a better data structure in Netlogo?

I'm scheduling tasks for agents (factories) to do over the next X times periods. For each task I am recording an Amount_To_Produce and an OrderID. I'm using a series of lists, two per day. For three time periods, it looks something like this.
TimePeriod 1
Amount_To_Produce, OrderID
5,100
6,101
2,102
TimePeriod 2
Amount_To_Produce, OrderID
10,103
5,101
20,104
TimePeriod 3
Amount_To_Produce, OrderID
5,100
5,105
This works OK: I'm processing each day one at a time with:
(foreach list1 ... command)
but if I want to extend it to more days it's a pain.
Plus I need to relate it to another two lists that store the agent that's buying the goods along with the OrderID (notice above that one order can spill over multiple days). But that bit is OK - it's really the need for lists for each day that is the problem.
I'll know how many days into the future the agents are planning, so it doesn't have to be created dynamically. The only other idea I have is:
Day, Amount_To_Produce, OrderID
1,5,100
1,6,101
1,2,102
2,10,103
2,5,101
2,20,104
3,5,100
3,5,105
The problem with this that foreach will process Day 1's orders three times, not once.
Anyway: does Netlogo have a better data structure for managing this sort of thing?
What I'd really like is for each agent to have its own database, a series of tables that the agent can query with an SQL type command (any chance we could get this in NL7.0?)
In the meantime, how would you store these data please?
extensions [table]
globals [tbl1 tbl2 listOfTables]
to test
set tbl1 table:make
set tbl2 table:make
set listOfTables (list tbl1 tbl2)
table:put tbl1 1 [[5 100] [6 101] [2 102]]
show listOfTAbles
end

Netlogo: Selecting an agent based on multiple conditions

I have 2 agents, hub and individual.
Individuals have its own variable called value.
I want to write a method that allow hub to select the individual with the highest value and has not established a link with the hub, in order to establish a link with it.
So far I am using max-one-of, which gives me the highest value-d individual the first round but on the second round the same individual is still selected despite a link has been already established with the hub.
I would like to ask all how do I get the individual that has not been linked with the hub yet, with the highest value?
Thank you very much!
You need to filter your individuals using with and link-neighbor?:
breed [ hubs hub ]
breed [ individuals individual ]
individuals-own [ value ]
to setup
clear-all
create-hubs 1
create-individuals 10 [
set value random 100
forward 5
]
reset-ticks
end
to go
ask hubs [
let candidates individuals with [ not link-neighbor? myself ]
if any? candidates [
create-link-with max-one-of candidates [ value ]
]
]
tick
end

Counting in the Subsummary AND over the Found Set, same value different fields - FileMaker 12

Hard to think of a good title for this.
I have a table with Agents and Referrals. The data shows in subsummary parts which are sorted by Agent.
It's easy to get a count when Agent = Referral.
However, is it possible to get a count of Referrals over the whole found set when sorted by Agent?
For example, Smith was the Agent for 10 records.
Smith was also the Referral for 8 records, 3 where Smith was the Agent and 5 where Jones was the agent.
On the subsummary part, sorted by Agent, I can get the 3 for when Smith is the Agent and Referral. How can I put on that same part that Smith is the Refferal for 8 records in the found set?
I was thinking of maybe Execute SQL but I don't know enough SQL to write a meaningful statement. Or should I go with that?
Thanks!
I'm not 100% clear on how you have this set up, but I'm going to assume you are only dealing with the two tables you mentioned -- Referrals, and Agents -- and that your report is based on the Referrals table, which has two relevant fields: Referrer, and Agent.
The first thing to realize is that, if you are trying to report on a found set of Referrals, subsummarized by Agent, you cannot have a Referral record show up in Smith's subsummary AND Jones' subsummary ... it is either/or.
I can think of a few ways to produce the report you are looking for:
Instead of reporting on the entire found set, report on smaller found sets (by person), and then assemble your report by appending each individual found set report to each other. For example: create a script that would find all Referrals with Smith as either the agent or the referrer, and that will give you a found set (and count) of 18 (from your example); iterate through all agents, and assemble the report from the collected data.
Create a new child table of the Referral table, with records for each instance of a Referral's referrer, as well as each instance of a Referral's agent (but only when different from the referrer) ... then, report from that table instead.
As you suggest, this sounds like it can be done using the ExecuteSQL command. I don't know what kind of output you are looking for, and your field names will be different (I used "AgentName", "agent", and "referrer"), but it would be something like:
Go To Layout [ "Agents" ]
Show All
Go To Record/Request [ First ]
Loop
Set Variable [ $ThisAgent ; AgentName & " referrals: " & Evaluate ( ExecuteSQL ( "SELECT 1 FROM Referrals WHERE ( agent LIKE 'SMITH' OR referrer LIKE 'SMITH')" ; "" ; "+" ) ) ]
Set Variable [ $ReportText ; List ( $ReportText ; $ThisAgent ) ]
Go To Record/Request [ Exit after last, Next ]
End Loop
set Variable [ $$MergeVariableForReportDisplay ; $ReportText ]