text:
Article Text

Prevalence of helmet use among motorcycle riders in Vietnam
1. D V Hung1,
2. M R Stevenson2,
3. R Q Ivers1
1. 1Injury and Musculoskeletal Division, The George Institute for International Health, University of Sydney, Sydney, New South Wales, Australia
2. 2Research and Development, The George Institute for International Health, University of Sydney, Sydney, New South Wales, Australia
1. Correspondence to:
 Dr D V Hung
 Injury and Musculoskeletal Division, the George Institute for International Health, the University of Sydney, Syndey, Australia, PO Box M201 Missenden Road, Sydney NSW 2050; vdan8956{at}mail.usyd.edu.au

Abstract

Objectives: To investigate the rate of helmet use among motorcycle drivers in Hai Duong province of Vietnam during winter/spring 2005, and to compare the rates of helmet use by road types.

Method: Population-based observational surveys.

Results: 16 560 motorcyclists were observed across 37 road sites (incorporating 5 road categories). The overall weighted average of helmet use for motorcyclists was 29.94%, with male drivers more likely to wear helmets than female drivers (odds ratio (OR) 1.64, 95% confidence interval (CI) 1.53 to 1.76). Male pillion passengers were less likely to wear helmets than female pillion passengers (OR 0.78, 95% CI 0.72 to 0.85). The number of adult drivers using helmets is larger as compared with that of young drivers (OR 8.56, 95% CI 5.93 to 12.19). The rates of helmet use were significantly higher (p<0.001) on compulsory roads and were 59.01%, 39.97%, 24.22%, 12.7% and 9.54% for national, provincial, district, commune and Hai Duong inner-city roads, respectively.

Conclusion: Helmet legislation has increased the rate of helmet use by motorcycle drivers on compulsory roads. Elsewhere, rate of helmet use is very low, indicating that in the absence of legislation and enforcement, motorcyclists in Vietnam will not wear a helmet.

• VKT, vehicle kilometers traveled

Statistics from Altmetric.com

Road traffic injuries are a global public health problem, with 1.2 million people killed and 50 million injured each year.1 Worldwide, the economic cost of road crash injuries is estimated to be about 1% of the gross national product in low-income countries and 1.5% in middle-income countries.1 Motorcycles are a common means of transportation in low-income and middle-income countries as they are cheap and accessible to many people. As a result, motorcycle-related injury has become a major public health concern in countries such as Vietnam. In particular, injuries to the head, after motorcycle crashes, are common causes of severe morbidity and mortality. Motorcycle helmets are designed to protect riders against head injuries and yet helmet use is not widespread in Vietnam.

In Vietnam, with a population of 81 million and increasing industrialization and urbanization, the number of motor vehicles has rapidly increased.2 In 2003, there were about 11.38 million registered motorcycles compared with 1.8 million motorcycles in 1992.3,4 Vietnam’s police data show that motorized two and three-wheelers accounted for 94.75% of all registered vehicles in 2005. Although no reliable data are available, the number of motorcycle injuries has also reportedly increased over the past years. For example, the number of reported road injuries rose from 14 174 in 1994 to 29 872 in 2002 and deaths rose from 4907 to 12 956.5 Recent surveys have reported that motorcycles account for 59% of road injuries and that they disproportionately affect the young.4 It has also been estimated that the cost of road traffic injury in Vietnam was at least 2% of the gross domestic product in 2000.4 To reduce deaths and injuries, the Vietnamese government promulgated the National Policy on Accidents and Injury Prevention in 2001, with the target of reducing traffic deaths from 14 to 9 per 10 000 vehicles by 2010.

Motorcycle helmets are effective in reducing head injury after a crash. According to the US National Highway Traffic Safety Administration, motorcycle helmets reduce the possibility of death in a crash by about 29%.6 A meta-analysis by Lui et al7 reported that motorcycle helmets reduce the risk of head injury by 72% and are also likely to reduce the risk of death, although the effectiveness may be modified by speed.

Several studies have suggested that helmet use differs by sex, age and position of the riders. Corad et al8 found that in Indonesia, only 20% of pillion passengers wore helmets compared with 89% of drivers. Similarly, in a Chinese study,9 only 29% of pillion passengers wore helmets compared with 63% of drivers. With respect to sex, studies in Thailand10 as well as in the US11 have found that women are more likely to report always wearing a helmet compared with men, with research indicating that the odds of a man wearing a helmet are half that of a woman (after controlling for riding position).12

Helmet legislation was first introduced in Vietnam in 2000, and a year later a further resolution was adopted that stipulated compulsory helmet use for all motorcycle riders on certain assigned routes and national roads.13–15 A financial penalty for not wearing a helmet while riding on compulsory roads was issued in February 2003, with a fine of VN$10 000–20 000 (US$ 0.7–1.5). Currently, there is no penalty for motorcyclists who use helmets that are incorrect or that are substandard. Despite such legislation, the rate of helmet use is unknown. The aim of this study was to measure and compare the prevalence of helmet use among motorcycle riders on different types of roads in Vietnam.

METHODS

A cross-sectional observational survey was undertaken in Hai Duong Province, located in the Red River Delta region, 60 km from Hanoi, with an area of 1649.55 km2 and a population of 1.67 million.16 The province comprises the city of Hai Duong and 11 districts. The urban population accounts for 14% of the total population. The road system in the province comprises six national roads with a total of 126.69 km in length, 20 provincial roads (336.87 km), district roads (359 km), commune roads (1388 km), inner-city roads of Hai Duong city (112.63 km) and village roads.16–18

The survey was undertaken in the province between February and April 2005. The population was defined as all motorcyclists riding on public roads in the province during the observation period. To ensure that the selection of road sites for the study was representative of the road structure for the province, a stratified random sample of roads reflecting the five road groups was used.

The observation sites were selected in two stages. For national and provincial roads, the first stage involved the random selection of the road. Assuming that the characteristics of traffic and helmet use are uniform along the length of the road, the second stage involved the selection of the observation site. The site was randomly selected after dividing the selected roads into 5-km segments. All national roads and 7 of 20 provincial roads were selected with one observation site for each selected road. For each observation site, we also nominated an alternative site, identified as the next 5-km segment. Alternative sites were used whenever the observation sites did not satisfy the criteria of site selection—namely, the presence of police at the time of observation, which we know artificially increases the prevalence of helmet wearing.19

District and commune roads were also sampled using a two-stage approach. Firstly, from the 12 districts identified, two districts were excluded (Cam Giang and Binh Giang) as these districts comprised <15% (13.94%) of the province’s population.20 In all, 7 of the 10 eligible districts were randomly selected. Within these districts, seven district roads and nine commune roads were randomly selected using simple random sampling from a sampling frame that comprised a list of all district and intercommune roads (provided by Hai Duong’s Department of Transportation).18 The second stage involved each selected road being divided into 1-km segments, of which one segment was randomly selected to be the observation site. The roads that were <1 km in length were considered to be one segment.

Hai Duong inner-city roads were sampled using the official map of the city as issued by Hai Duong’s Department of National Resources and Environment, and the entire list of roads provided by the city’s Division of Urban Administration.21 Roads that were <0.5 km in length and 5 m in width were excluded because of low traffic volumes. Six roads were randomly selected from all remaining roads and were divided into segments (one segment is defined as the road between two intersections), and one segment was randomly selected for one selected road. Observations were undertaken about 100–200 m from the randomly selected intersection.

All observation sites were established at a non-curved road segment. At each site, two trained observers, including the researchers (DVH), made the observations. The observer completed the observation form, recording all passing motorcycles and transcribing the following: number of riders, goods carried, sex of riders (male or female), age of riders (adult or child) and helmet use (correctly or incorrectly fastened). Riders who were not seated on their own (namely, babies or infants) were excluded from the observation. Observations were conducted between 09:00 and 17:00 during weekdays. Both directions of traffic at each site were observed until the required number of observations was obtained.

To minimize missing data on roads with high traffic volume, one observer observed motorcycles with only a single driver and the other observed motorcycles with ⩾1 passenger. Whenever possible, the two observers cooperated to reach agreement on the required parameters to be recorded. On roads with low traffic volume, the registration number of motorcycles was noted to avoid double recording. Along with the direct observation, a video camera was used to record traffic flow at sites with extensive traffic flows and high-speed traffic.

The proposed sample size was such that it could (1) detect a hypothesized proportion of helmet use among motorcycle riders with a relative error of 1% and a 95% confidence interval (CI) and (2) detect a difference in the proportions of helmet use between specific types of roads with an α = 0.05 and 80% power. About 16 000 vehicle observations were collected to meet the above assumptions.

Stratum-specific helmet use rates were calculated by applying the weight defined by the formula

where Wij is the weight of road j in road type i, Pij is the observed proportion of helmet use and k is the number of roads selected within road type i. Wij is calculated on the basis of the estimated vehicle kilometers traveled (VKT) given by equation 2:

where Lij is total length for road j among road type i and Vij is the estimated traffic volume of road j among road type i. We assumed that the traffic volume was constant along the whole road.

The population helmet use rate was calculated using the weighted applied road type (Wi), which is defined as the proportion of VKT of motorcycles on each road type (Vi) given that the volume is constant across the road type, as given in equation 3:

where Li is the total length for road type i and Vi is the average estimated traffic volume of road type i, calculated by dividing the estimated VKT for selected roads by the total length of selected roads.

The estimated population proportion of helmet use was calculated by equation 4:

Standard error (√(p(1-p)/n)) and 95% CI of the estimates were calculated to check the precision of the estimates.

To compare the rates of helmet use between stratums of roads, one-sided, two-sample z tests were used with unequal sample sizes with a significance level of 0.05 and a power of 80%. Data were stratified by road type to compare helmet use by sex and age group and Mantel–Haenszel weighted odds ratios (ORMH) were calculated. 95% CI values for the difference were also calculated using unequal sample size for each stratum of road.22 χ2 for linear trend in proportion (Mantel extension) of helmet use was calculated with five levels of roads. Logistic regression was used with stepwise selection to investigate the predictors of helmet use. All data were analyzed using SAS v.8.02.

RESULTS

A total of 16 560 drivers and 8626 passengers from 37 randomly selected sites were observed, among which 45 met the exclusion criteria; for 29 motorcyclists, the sex was not recorded. Both baby or infant and sex-missing data accounted for 0.32% of all motorcyclists or 1.07% of total pillion passengers. Of the observed motorcycles, 63.10% (n = 10 450) did not have a pillion passenger, with the remainder having one (32.88%, n = 5445), two (3.71%, n = 614), or three pillion passengers (0.31%, n = 51). Local roads (inner-city roads and commune roads) had the highest proportion of motorcycles without a pillion passenger (73.72%). Of the observed drivers, 83.29% (13 971) were men and 16.71% (2589) were women corresponding to a male:female ratio of 5.4:1. Almost all (99.88%, n = 16 540) of the drivers were aged ⩾16 years. A total of 22 691 motorcyclists were identified as adults and 650 were recorded as children. In all, 9% (n = 1496) of motorcycle drivers carried large goods on their motorcycles. Among 6752 pillion passengers, 55% were women (n = 3713) and the remaining 3039 were men or children (n = 630).

Overall, the weighted prevalence rate of helmet use among motorcycle drivers was low—29.94% (standard error (SE) = 0.3%; table 1). The rates of helmet use were highest on national roads (fig 1) with weighted stratum-specific helmet use rates of 58.99%, followed by provincial roads (prevalence rate 39.97%), and were lowest on inner-city roads (prevalence rate 9.54%). The difference in the rate of helmet use across all road types was significant (χ2  = 3936.6, df = 4; p<0.001). Almost 32% (n = 7236) of adults wore a helmet compared with 5.23% (34/650) of children (OR 8.45, 95% CI 5.93 to 12.19).

Table 1

Helmet use by road type and by position of riders

Figure 1

Helmet use by road type (using weighted proportions).

Of the 16 560 drivers, the weighted prevalence of helmet use was 34.69% compared with 18.97% for pillion passengers. After stratification by road type, drivers were two times as likely to wear a helmet than passengers (ORMH 2.39, 95% CI 2.29 to 2.53). This trend was the same for all strata of roads (table 1). Table 2 shows the comparison of helmet use rates among male and female drivers. After stratification by road type, male drivers were more likely to wear a helmet compared with female drivers on all road types (ORMH 1.64, 95% CI 1.53 to 1.76).

Table 2

Helmet use by sex

Of 6781 pillion passengers, the weighted prevalence of helmet use was 18.97%, significantly lower than that for drivers (p<0.001). Male pillion passengers were less likely to wear a helmet compared with female pillion passengers after controlling for road type (ORMH 0.78, 95% CI 0.72 to 0.85). Adult pillion passengers were more likely to wear a helmet than children (OR 5.01, 95% CI 3.49 to 7.23).

Helmet use for 146 (0.63%) riders was recorded as “incorrect use”, indicating that the chin strap was either not fastened or incorrectly fastened. These observations were excluded from the number of riders wearing helmets. Additionally, 284 (1.22%) riders were coded as “helmet present but not worn”; such observations were also excluded from the analysis.

Of the 1496 motorcyclists carrying large goods, 47% (n = 716) of the drivers wore a helmet. Drivers identified to be carrying goods were more likely to wear helmets than those who were not carrying goods (ORMH 1.68, 95% CI 1.56 to 1.82).

Table 3 describes the predictors for helmet use of drivers. The strongest predictor for helmet use was the type of road traveled on. An almost fivefold (OR 4.86, 95% CI 4.53 to 5.21) likelihood of wearing a helmet was observed while traveling on a road that required, by legislation, motorcyclists to wear a helmet compared with roads that had no such legislation.

Table 3

Predictors of helmet use among motorcycle drivers*

DISCUSSION

In this study, we found a higher rate of helmet use on roads with legislation requiring compulsory helmet use, albeit with a low prevalence, than on roads without such requirements. The difference in the prevalence of helmet use between road types indicates that helmet legislation, in combination with its enforcement, has an effect on the rates of helmet use. Our results show that riders on national roads are more likely to wear a helmet compared with those traveling on provincial roads, despite the fact that legislation dictates helmet use while traveling on both road types. These observed large variations in helmet use on roads with compulsory helmet use suggest that law enforcement of helmet legislation is not consistent.

We found that pillion passengers were less likely to wear helmets than drivers, and these results are consistent with those of other studies in developing countries such as Indonesia and8 China9 as well as in developed countries.12,23,24 Similar to previous research, we also found that adults are more likely to wear helmets than children.11,12,19

In contrast with other studies,11,12,27 we found that male drivers were more likely to wear a helmet than female drivers. This is a surprising finding and is difficult to explain without exploring the reasons further with riders or drivers, which was not the purpose of this study and clearly warrants further investigation.

In accordance with previous studies,25,26 we observed involvement in motorcycle use is greater in males compared with females. Given the lower rate of helmet use among women, children and pillion passengers, we recommend both increased awareness of the implications of head injury after a motorcycle crash and fines for drivers carrying pillion passengers not wearing a helmet. We acknowledge that fines may be premature, given that there are few helmets currently available for young children.

As is evident from this study, making helmet use compulsory (as it is on several road types in Hai Duong) increases the likelihood of a driver using a helmet almost fivefold. This finding mirrors those reported by Ichikawa et al,10 who found that helmet legislation increased helmet use fivefold in Thailand. However, the fact that the prevalence of helmet use on compulsory roads is still <60%, suggests that greater levels of enforcement are required.

This study has several limitations. Firstly, the study was conducted during the winter/spring seasonal period, a period, that may confer higher rates of helmet use than if observed during summer/autumn, when it is hot and humid. Therefore, the observed rates of helmet use may be overestimated. Secondly, the classification of roads was based on the government’s management scheme rather than the key determinants of the road such as its length or paving material. Thirdly, because of a lack of data on traffic volume, the volume estimates (used for the weightings) were obtained by dividing the number of motorcycles traveled on the specific road during the observational period. Finally, observation of incorrect helmet use is likely to be underestimated as, in the absence of stopping the motorcyclists, it was difficult to identify the status from a distance. Similarly, assigning the age of the driver or rider may have been arbitrary, although we minimized the error by grouping age into only two categories. Importantly, attempts to minimize these errors were undertaken by video recording and reviewing the footage and, in relation to the age of the driver or rider, recent research has shown that assignment of age by independent observers is relatively high (⩾87%).28

CONCLUSION AND IMPLICATIONS FOR INJURY PREVENTION

The prevalence of helmet use by motorcycle drivers is influenced by the presence of legislation and enforcement. Currently, in Vietnam, legislation for helmet use applies on only certain assigned routes and national roads, and the prevalence of helmet use on these roads has reached a prevalence of almost 60%, which is five times the prevalence on city roads. Clearly, in the absence of legislation and enforcement, Vietnam’s motorcyclists do not wear helmets. Given the large number of motorcycles in Vietnam and the increasing burden due to motorcycle-related injuries, there is now an urgent need for the government to introduce a consistent policy on helmet use by motorcycle drivers—a policy that applies to all road types and for all motorcyclists. Until such time as a population-based response to motorcycle-related injury is adopted, it is unlikely that major reductions in serious head injury will be observed.

Key points

• Overall, the prevalence of helmet use for drivers is 34.6% and even lower for pillion passengers—18.9%.

• The prevalence of helmet use is higher on roads with legislation requiring compulsory helmet use.

• The prevalence of helmet use varies between road types that have legislation requiring compulsory helmet use, indicating that enforcement of the legislation is not consistent across road types.

• Given the large number of motorcycles in Vietnam and the increasing burden due to motorcycle-related injuries, there is an urgent need for the government to introduce a consistent policy on helmet use by motorcycle drivers—a policy that applies to all road types and for all motorcyclists.

Acknowledgments

We acknowledge Hai Duong’s Provincial Health Service and Hai Duong’s Department of Transportation and the Division of Urban Administration of Hai Duong City People Committee for providing road data, maps and legislative documents. We thank Dang Hong Son and Nguyen Huu Hai—the trained observers who spent countless time on the roads to conduct observations. We also thank Dr Nguyen Thanh Cong, Director of Hai Duong Provincial Health Service, for support.

Footnotes

• Funding: DVH was funded by a doctoral scholarship from the Australian Agency for International Development. Financial assistance for this project was provided by The George Institute for International Health, Sydney, Australia.

• Competing interests: None declared.

• Contributors: DVH conceived the study, implemented all field activities, performed data entry, analyzed and led the writing. MRS assisted the study with methods, and supervised the analysis and writing. RQI helped with the literature review and writing. All authors helped to conceptualize ideas, interpret findings and review the final draft of the manuscript.

Request Permissions

If you wish to reuse any or all of this article please use the link below which will take you to the Copyright Clearance Center’s RightsLink service. You will be able to get a quick price and instant permission to reuse the content in many different ways.


text:
# Memory Management

This section is about memory management in the kernel: how the kernel manages memory, and how to manage memory as a kernel developer.

## Pages

A page is a block of virtual memory. Pages are the basic unit of memory management in the kernel [1, P. 231].

Each architecture determines its page size, and many architectures can support multiple page sizes. Most 32-bit architectures support 4KB pages, and most 64-bit architectures support 8KB pages [1, P. 231].

The kernel represents a physical page with the page struct, defined in <linux/mm_types.h>. A simplified copy of the struct is:

struct page {
unsigned long flags;
atomic_t _count;
atomic_t _mapcount;
unsigned long private;
pgoff_t index;
void *virtual;
};

The flags field stores the status of the page. For example, whether the page is dirty or not, or whether the page is locked in memory.

The _count field stores the usage count of the page, i.e., how many references there are to the page. If _count is -1 then the page is free [1, P. 232].

The virtual field is the page’s virtual address. Although this is normally the page’s virtual memory address, some memory (called high memory) isn’t permanently mapped in the kernel’s address space. For high memory the value will be NULL [1, P. 232].

## Zones

Zones are groups of pages with similar hardware-assigned properties (e.g., DMA zones, normal zones) [1, P. 233].

There are two main hardware limitations that are relevant to zones:

1. Some hardware devices can only perform DMA (Direct Memory Access) to certain address spaces.
2. Some architectures can physically address larger areas than they can virtually address. In these cases some memory is not permanently mapped into the kernel address space.

[1, P. 233]

There are four primary address zones:

1. ZONE_DMA contains pages that can undergo DMA.
2. ZONE_DMA32 contains pages that can undergo DMA and are only accessible by 32-bit devices.
3. ZONE_NORMAL contains normal pages.
4. ZONE_HIGHMEM contains high memory.

[1, P. 233]

Memory layout and usage is architecture-specific. For architectures that can perform DMA into any memory address ZONE_DMA is empty, and ZONE_NORMAL is used for allocation, whereas for other architectures ZONE_DMA could contain all memory in the range 0-16MB [1, P. 233].

ZONE_NORMAL tends to be what is remaining after ZONE_DMA and ZONE_HIGHMEM. The following table shows the zones on an x86 architecture:

Zone Description Physical Memory
ZONE_DMA DMA-able pages. < 16MB
ZONE_NORMAL Normally addressable pages. 16–896MB
ZONE_HIGHMEM Dynamically mapped pages. > 896MB

[1, P. 234]

Zones are used during page allocation where some allocations require pages from a particular zone. Allocations must come from a single zone at once [1, P. 234].

Each zone is represented by a zone struct:

struct zone {
unsigned long watermark[NR_WMARK];
unsigned long lowmem_reserve[MAX_NR_ZONES];
struct per_cpu_pageset pageset[NR_CPUS];
spinlock_t lock;
struct free_area free_area[MAX_ORDER]
spinlock_t lru_lock;
struct zone_lru {
unsigned long nr_saved_scan;
} lru[NR_LRU_LISTS];
struct zone_reclaim_stat reclaim_stat;
unsigned long pages_scanned;
unsigned long flags;
atomic_long_t vm_stat[NR_VM_ZONE_STAT_ITEMS];
int prev_priority;
unsigned int inactive_ratio;
unsigned long wait_table_hash_nr_entries;
unsigned long wait_table_bits;
struct pglist_data *zone_pgdat;
unsigned long zone_start_pfn;
unsigned long spanned_pages;
unsigned long present_pages;
const char *name;
};

## Memory allocation

Memory allocation is the process of assigning sections of memory.

The main function to allocate memory from the kernel is alloc_pages():

struct page * alloc_pages(gfp_t gfp_mask, unsigned int order)

This allocates $2^\text{order}$ contiguous pages, and returns a pointer to the first page’s page struct [1, P. 235].

You can convert a given page to its logical address with page_address():

void * page_address(struct page *page)

page_address() returns a pointer to the logical address where the given physical page currently resides. If you have no need for the actual page struct, you can call __get_free_pages():

unsigned long __get_free_pages(gfp_t gfp_mask, unsigned int order)

__get_free_pages() works like alloc_pages() except it returns the logical address of the first page, instead of the page struct.

If you just need a single page, you can use the following helper functions:

struct page * alloc_page(gfp_t gfp_mask)

get_zeroed_page() returns a page filled with zeros:

unsigned long get_zeroed_page(unsigned int gfp_mask)

get_zeroed_page()should be used when pages are given to user space, because the previous memory might have contained sensitive information.

You free pages with the free() family of functions:

void __free_pages(struct page *page, unsigned int order)
void free_pages(unsigned long addr, unsigned int order)

kmalloc() can be used to allocate byte-size chunks. kmalloc() works similarly to malloc(), except it also takes a flags parameter. kmalloc() returns a pointer to a chunk of memory at least bytes size in length that is physically and virtually contiguous [1, P. 238].

Memory allocated with kmalloc() is freed with kfree().

A alternative to kmalloc() is vmalloc(). vmalloc() returns a chunk of virtually contiguous memory (with no guarantees that it’s physically contiguous) [1, P. 244].

GFP (Get Free Page) mask flags are flags that are passed to kernel allocator functions [1, P. 238]

GFP flags are represented with the gfp_t type. There are three types of flags:

• Action modifiers—how the kernel should allocate memory.
• Zone modifiers—what zone to allocate from.
• Type flags—a combination of a zone and an action type.

[1, Pp. 238-9]

You can see the action modifiers in the following table:

Flag Description
__GFP_WAIT The allocator can sleep.
__GFP_HIGH The allocator can access emergency pools.
__GFP_IO The allocator can start disk I/O.
__GFP_FS The allocator can start filesystem I/O.
__GFP_COLD The allocator should use cache cold pages.
__GFP_NOWARN The allocator does not print failure warnings.
__GFP_REPEAT The allocator repeats the allocation if it fails, but the allocation can potentially fail.
__GFP_NOFAIL The allocator indefinitely repeats the allocation. The allocation cannot fail.
__GFP_NORETRY The allocator never retries if the allocation fails.
__GFP_NOMEMALLOC The allocator does not fall back on reserves.
__GFP_HARDWALL The allocator enforces “hardwall” cpuset boundaries.
__GFP_RECLAIMABLE The allocator marks the pages reclaimable.
__GFP_COMP The allocator adds compound page metadata (used internally by the hugetlb code).

[1, P. 239]

These flags can be specified together. For example:

ptr = kmalloc(size, __GFP_WAIT | __GFP_IO | __GFP_FS);

Zone modifiers specify the zones that a memory allocation should originate from. Normally the allocation will happen from any zone, with the kernel preferring ZONE_NORMAL.

You can see the zone modifiers in the following table:

Flag Description
__GFP_DMA Allocates only from ZONE_DMA
__GFP_DMA32 Allocates only from ZONE_DMA32
__GFP_HIGHMEM Allocates from ZONE_HIGHMEM or ZONE_NORMAL

[1, P. 240]

#### Type Flags

The type flags are a combination of action modifiers and zone modifiers, which makes allocations easier.

You can see the type flags in the following table:

Flag Description
GFP_ATOMIC The allocation is high priority and must not sleep. This is the flag to use in interrupt handlers, in bottom halves, while holding a spinlock, and in other situations where you cannot sleep.
GFP_NOWAIT Like GFP_ATOMIC, except that the call will not fallback on emergency memory pools. This increases the liklihood of the memory allocation failing.
GFP_NOIO This allocation can block, but must not initiate disk I/O. This is the flag to use in block I/O code when you cannot cause more disk I/O, which might lead to some unpleasant recursion.
GFP_NOFS This allocation can block and can initiate disk I/O, if it must, but it will not initiate a filesystem operation. This is the flag to use in filesystem code when you cannot start another filesystem operation.
GFP_KERNEL This is a normal allocation and might block. This is the flag to use in process context code when it is safe to sleep. The kernel will do whatever it has to do to obtain the memory requested by the caller. This flag should be your default choice.
GFP_USER This is a normal allocation and might block. This flag is used to allocate memory for user space processes.
GFP_HIGHUSER This is an allocation from ZONE_HIGHMEM and might block. This flag is used to allocate memory for user space processes.
GFP_DMA This is an allocation from ZONE_DMA. Device drivers that need DMA-able memory use this flag, usually in combination with one of the preceding flags.

[1, Pp. 241-2]

The majority of allocations in the kernel use the GFP_KERNEL flag which creates a normal priority memory allocation that might sleep (thus it must only be used when it’s safe to sleep) [1, P. 242].

## Slab allocation

Slab allocation is a mechanism for efficient memory allocation of objects. Slab allocation reduces memory fragmentation compared to earlier approaches [1, P. 246].

In the kernel, a slab allocator divides objects into groups called caches. Each cache stores a different object (e.g. one cache for task_struct structs, another for inode structs) [1, P. 246].

Caches are divided into slabs. A Slab consists of one or more contiguous pages that contains a number of objects of the data structure that’s being cached [1, P. 246].

A slab is in one of three states: full, partial, or empty. When the kernel requests a new object, the request is satisfied by a partial slab if one exists, otherwise an empty slab is used [1, P. 246].

A cache is represented with the kmem_cache struct. kmem_cache contains three slab lists stored inside a kmem_list3 struct: slabs_full, slabs_partial, and slabs_empty.

A slab struct represents a slab:

struct slab {
struct list_head list; /* full, partial, or empty list */
unsigned long colouroff; /* offset for the slab coloring */
void *s_mem; /* first object in the slab */
unsigned int inuse; /* allocated objects in the slab */
kmem_bufctl_t free; /* first free object, if any */
};

The slab allocator creates new slabs with the __get_free_pages() function:

static void *kmem_getpages(struct kmem_cache *cachep, gfp_t flags, int nodeid)
{
struct page *page;
int i;

flags |= cachep->gfpflags;
if (likely(nodeid == -1)) {
return NULL;
} else {
page = alloc_pages_node(nodeid, flags, cachep->gfporder);
if (!page)
return NULL;
}

i = (1 << cachep->gfporder);
if (cachep->flags & SLAB_RECLAIM_ACCOUNT)
while (i––) {
SetPageSlab(page);
page++;
}
}

Memory is freed with kmem_freepages(), which calls free_pages() on the given cache’s pages. The freeing function is only called when available memory grows low, or when a cache is explicitly destroyed [1, P. 249].

A new cache is created with kmem_cache_create():

struct kmem_cache * kmem_cache_create(const char *name,
size_t size,
size_t align,
unsigned long flags,
void (*ctor)(void *));

name is the cache name. size is the size of each element in the cache. align is the offset of the first element in a cache, this is done to ensure a particular alignment in the first page. ctor is a constructor for the cache. It’s called whenever a new item is added to the cache. You can pass NULL for ctor [1, Pp. 249-50].

flags is a flags parameter used to control the behavior of the cache. It takes the following options:

• SLAB_HWCACHE_ALIGN—instructs the slab layer to align each object within a slab to a cache line.
• SLAB_POISON—causes the slab layer to fill the slab with a known value. This is called poisoning, and can be useful to catch access to uninitialized memory.
• SLAB_RED_ZONE—causes the slab layer to insert red zones around the cache to detect buffer overflows.
• SLAB_PANIC—causes the kernel to panic if slab allocation fails.
• SLAB_CACHE_DMA—instructs slab layer to allocate each slab in DMA-able memory.

[1, Pp. 249-50]

On success, kmem_cache_create() returns a pointer to the created cache. To destroy a cache, you call kmem_cache_destroy():

int kmem_cache_destroy(struct kmem_cache *cachep)

Once a cache is created, you can allocate objects from it using kmem_cache_alloc():

void * kmem_cache_alloc(struct kmem_cache *cachep, gfp_t flags)

To later free an object and return it to its originating slab, use kmem_cache_free():

void kmem_cache_free(struct kmem_cache *cachep, void *objp)

This marks the object objp in cachep as free [1, P. 251].

## High Memory Mappings

High memory is memory that isn’t permanently mapped into the kernel address space [1, P. 253].

Pages obtained via alloc_pages() with the __GFP_HIGHMEM flag might not have a logical address [1, P. 253].

To map a page structure into the kernel’s address space, use kmap, declared in <linux/highmem.h>:

void *kmap(struct page *page)

kmap() works on both high memory and low memory. If the page structure represents a page in low memory, then the virtual address is returned. If the page is in low memory, a permanent mapping is created and the address is returned. kmap() might sleep, so it works only in process context [1, P. 254].

Since the number of permanent mappings of high memory are limited, you should unmap high memory when it’s no longer needed. You do this with the kunmap() function.

When you need to create a mapping but the current context can’t sleep, you can create a temporary mapping which uses a reserved mapping [1, P. 254].

Setting up a temporary mapping is done with kmap_atomic():

void *kmap_atomic(struct page *page, enum km_type type)

The mapping is undone wit kunmap_atomic().

## References

1. [1] L. R., Linux Kernel Development (Developer’s Library), 3rd ed. Addison-Wesley Professional, 2010.

format: plain


text:
## Elementary and Intermediate Algebra: Concepts & Applications (6th Edition)

$16{{x}^{2}}+25{{y}^{2}}=1$ Now write $16=\frac{1}{\frac{1}{16}}$ and $25=\frac{1}{\frac{1}{25}}$, so rewrite the equation. $\frac{{{x}^{2}}}{\frac{1}{16}}+\frac{{{y}^{2}}}{\frac{1}{25}}=1$ Standard equation of an Ellipse is: $\frac{{{x}^{2}}}{{{a}^{2}}}+\frac{{{y}^{2}}}{{{b}^{2}}}=1$ Identify $a\text{ and }b$ by comparing the equation with the standard equation, \begin{align} & \frac{{{x}^{2}}}{\frac{1}{16}}+\frac{{{y}^{2}}}{\frac{1}{25}}=1 \\ & \frac{{{x}^{2}}}{{{\left( \frac{1}{4} \right)}^{2}}}+\frac{{{y}^{2}}}{{{\left( \frac{1}{5} \right)}^{2}}}=1 \end{align} Since $a=\frac{1}{4}\text{ and }b=\frac{1}{5}$, the x-intercepts are $\left( -\frac{1}{4},0 \right)\text{ and }\left( \frac{1}{4},0 \right)$ and the y-intercepts are $\left( 0,-\frac{1}{5} \right)\text{ and }\left( 0,\frac{1}{5} \right)$. Since ${{a}^{2}}>{{b}^{2}}$, the ellipse will be horizontal. Plot this point and connect them with the oval shaped curve.


text:
# Combination Theorem for Continuous Functions/Product Rule

## Theorem

Let $X$ be one of the standard number fields $\Q, \R, \C$.

Let $f$ and $g$ be functions which are continuous on an open subset $S \subseteq X$.

Then:

$f g$ is continuous on $S$

where $f g$ denotes the pointwise product of $f$ and $g$.

## Proof

By definition of continuous:

$\forall c \in S: \displaystyle \lim_{x \mathop \to c} \map f x = \map f c$
$\forall c \in S: \displaystyle \lim_{x \mathop \to c} \map g x = \map g c$

Let $f$ and $g$ tend to the following limits:

$\displaystyle \lim_{x \mathop \to c} \map f x = l$
$\displaystyle \lim_{x \mathop \to c} \map g x = m$

From the Product Rule for Limits of Functions:

$\displaystyle \lim_{x \mathop \to c} \paren {\map f x \, \map g x} = l m$

So, by definition of continuous again, we have that $f g$ is continuous on $S$.

$\blacksquare$


text:
# Pizza War 1

Classical Mechanics Level 3

Vaibhav gives a challenge to Kalash. He says that describe a motion such that the velocity vector at some instant of time makes an angle of $$45^{\circ}$$ with the acceleration vector. Kalash then swiftly answers that $$\vec{r} = at\hat{i} + at\left(1 - \dfrac{t}{10}\right)\hat{j}$$.

Kalash then asks Vaibhav at what instant of time will this occur for the motion described above. Vaibhav is confused. Can you help him out?

×


text:
#59 | Impact of Inductive Effect: II
(Chemistry) > Organic Chemistry - Some Basic Principles And Techniques


text:
# Minimario's triangles

Geometry Level pending

In triangle $$\triangle ABC$$, $$AB=30$$ and $$AC=28$$. Point $$D$$ lies on line segment $$AB$$ such that $$BD=16$$ and point $$E$$ lies on line segment $$AC$$ such that the area of quadrilateral $$BCED$$ is $$\frac{7}{10}$$th of the area of triangle $$\triangle ABC$$. Find the length of $$AE$$.

This problem is posed by Minimario M.

×


text:
# util¶

The util module provides a collection of general purpose methods.

nutils.util.sum()

reduce(function, sequence[, initial]) -> value

Apply a function of two arguments cumulatively to the items of a sequence, from left to right, so as to reduce the sequence to a single value. For example, reduce(lambda x, y: x+y, [1, 2, 3, 4, 5]) calculates ((((1+2)+3)+4)+5). If initial is present, it is placed before the items of the sequence in the calculation, and serves as a default when the sequence is empty.

nutils.util.product()

reduce(function, sequence[, initial]) -> value

Apply a function of two arguments cumulatively to the items of a sequence, from left to right, so as to reduce the sequence to a single value. For example, reduce(lambda x, y: x+y, [1, 2, 3, 4, 5]) calculates ((((1+2)+3)+4)+5). If initial is present, it is placed before the items of the sequence in the calculation, and serves as a default when the sequence is empty.

class nutils.util.NanVec(length)

Bases: numpy.ndarray

nan-initialized vector

nutils.util.tri_merge(tri, x, mergetol=0)

Create connected triangulation by connecting (near) identical points.

Based on a set of coordinates x, create a modified copy of tri with any occurrence of j replaced by i if x[i] equals x[j] within specified tolerance. The result is a triangulation that remains valid for any associated data vector that follows the same equality relations.

Example:

>>> x = [0,0], [1,0], [0,1], [1,0], [1,1] # note: x[1] == x[3])
>>> tri = [0,1,2], [2,3,4]
>>> tri_merge(tri, x)
array([[0, 1, 2],
[2, 1, 4]])

Requires scipy.

Parameters
• x (float array) – Vertex coordinates.

• tri (int array) – Triangulation.

• mergetol (float (optional, default 0)) – Distance within which two points are considered equal. If mergetol == 0 then points are considered equal if and only if their coordinates are identical. If mergetol > 0 (required scipy) then points are considered equal if they are within euclidian distance < mergetol. If mergetol < 0 then tri is returned unchanged.

Returns

merged_tri

Return type

int array

class nutils.util.tri_interpolator(tri, x, mergetol=0)

Bases: object

Interpolate function values defined in triangulation vertices.

Convenience object that implements 2D interpolation on top of matplotlib’s triangulation routines. Unlike matplotlib’s own LinearTriInterpolator, the tri_interpolator allows for interpolation of multi-dimensional arrays, as well as repeated interpolations of different vertex values.

The arguments are identical to tri_merge().

After instantiation of the interpolator object, interpolation coordinates are specified via the object’s getitem operator. The resulting callable performs the interpolation:

>>> trix = [0,0], [1,0], [0,1], [1,1] # vertex coordinates
>>> triu = 0, 0, 10, 0 # vertex values
>>> interpolate = tri_interpolator([[0,1,2],[1,3,2]], trix)
>>> x = [.1,.1], [.1,.9], [.9,.9] # interpolation coordinates
>>> u = interpolate[x](triu) # interpolated values

Requires matplotlib.

__weakref__

list of weak references to the object (if defined)

nutils.util.obj2str(obj)

compact, lossy string representation of arbitrary object

nutils.util.single_or_multiple(f)

Method wrapper, converts first positional argument to tuple: tuples/lists are passed on as tuples, other objects are turned into tuple singleton. Return values should match the length of the argument list, and are unpacked if the original argument was not a tuple/list.

>>> class Test:
...   @single_or_multiple
...   def square(self, args):
...     return [v**2 for v in args]
...
>>> T = Test()
>>> T.square(2)
4
>>> T.square([2,3])
(4, 9)

Parameters

f (callable) – Method that expects a tuple as first positional argument, and that returns a list/tuple of the same length.

Returns

Wrapped method.

nutils.util.positional_only(*names, keep_varpositional=False)

Add var-positional arguments to function signature.

Python has no explicit syntax for defining positional-only parameters, but the effect can be achieved by using a var-positional argument and unpacking it inside the function body. The positional_only() decorator adds a check for the number of positional arguments provided, and updates the function signature to reflect this design. It requires that the first argument is var-positional, precluding positional-or-keyword arguments.

Example:

>>> @positional_only('x')
... def f(*args, **kwargs):
...   x, = args
>>> inspect.signature(f)
<Signature (x, /, **kwargs)>

>>> @positional_only('x', keep_varpositional=True)
... def f(*args, **kwargs):
...   x, *args = args
>>> inspect.signature(f)
<Signature (x, /, *args, **kwargs)>

Parameters
• names (variable argument list of str) – Names of the positional-only arguments, in order.

• keep_varpositional (bool (default: False)) – If True, retain the var_positional argument.

nutils.util.loadlib(**libname)

Find and load a dynamic library using ctypes.CDLL. For each (supported) platform the name of the library should be specified as a keyword argument, including the extension, where the keywords should match the possible values of sys.platform. In addition to the default directories, this function searches site.PREFIXES and site.getuserbase().

Example

To load the Intel MKL runtime library, write:

loadlib(linux='libmkl_rt.so', darwin='libmkl_rt.dylib', win32='mkl_rt.dll')

nutils.util.readtext(path)

path (os.PathLike, str or io.TextIOBase) – Path-like or file-like object pointing to the data to be read.
File data as str.


text:
# Supercharge your learning!

Use adaptive quiz-based learning to study this topic faster and more effectively.

# Complement of a set

The complement of a subset $A$ of $E$ consists of all the elements in $E$ that are not in $A$. It is written as $A'$ or $A^c$.

The complement of the set of the odd numbers is the set of even numbers (with the set of integers as the reference set).

The complement of the set of the vowels is the set of the consonants (with the set of English letters as the reference set).

The reference set $E$ is often omitted when it is clear which set we are referring to.

The complement of the complement of a set is the original set $$(A')' = A.$$

The blue region is the complement of the white region


text:
# Prove that for all integers $a$ and $b$, if $a\mid b$ then $a^2\mid 3b^2$

Hello I'm having trouble finding a proof for this problem. I have the following proof so far....

Suppose $a$ and $b$ are particularly chosen integers such that $a\mid b$.

By definition of divisibility $b= a\cdot k$ for some integer $k$.

Then,

$a^2 \mid 3b^2$

$a^2 \cdot k = 3b^2$

Where should I go after this step? Is this correct?

Let $t = a^2 \cdot k$ because the product of integers are integers.

Therefore

$t \mid 3b^2$

• Since $b=ak$, we have $3b^2=3(ak)^2=a^2(3k^2) \ldots$ – Francesco Polizzi Jul 2 '18 at 21:33
• I can see how 3b² = 3(ak)² but cant see how that is equivalent to a²(3k²) . Could you explain a bit? And what would be the correct category to ask this question? – Jlee Jul 2 '18 at 21:47
• Maybe the answers posted here can help you: Show that for all integers $a$ and $b$ if $a\mid b$ then $a^2\mid b^2$ – Martin Sleziak Jul 3 '18 at 11:00
• @Jlee As Francesco Polizzi has explained above, just square both sides of $b=ak$ and rearrange to get the desired conclusion. – Allawonder Jul 3 '18 at 11:03
• "I can see how 3b² = 3(ak)² but cant see how that is equivalent to a²(3k²) " That's just rewriting. Commutativity and associativtiy. $3(ak)^2 = 2\times a\times k\times a\times k = a\times a\times 3\times k\times k = a^2(3k^2)$. This was not meant to be tricky. – fleablood Jul 4 '18 at 4:00

You have things backward. Your first sentence is right, that $b=ak$. But then you leap to the very end and state that "Then $a^2 \mid 3b^2.$" But that's your conclusion. It should be the last sentence of your proof.
You need to start with $b=ak$ and work your way to $3b^2 = a^2n$ (for some integer $n$) and then you can conclude that $a^2 \mid 3b^2.$
You might write: Well, $b=ak$, so $b^2 = a^2k^2$, so $3b^2 = 3a^2k^2 = a^2(3k^2).$ Since $3k^2$ is an integer,$\ldots$
It's even easier than that. if $a \mid b$, then perforce $a^2 \mid b^2$ and hence $a^2 \mid nb^2$ for all integers $n$, including $3$.


text:
# The meaning of expected value for discrete random variable in dice experiments

Does the expected value always speak to a payoff? Or can the expected value be thought of independent of payoffs?

I don't understand when we say a fair die has an expected value of 3.5. Does that mean we should expect to roll a 3 or 4 most of the time, or that if we had to pay for each roll and the payout was 1 dollar for 1, 2 dollars for 2, etc., that you shouldn't pay more than $3.5 per roll because in the long run that would be fair (meaning we'd break even). • It's just historic terminology for the average over possibilities. As with 3.5 for throwing a die with 6 sides, the "expectation" does not even have to be a feasible value. Jul 13, 2016 at 18:48 • Value here doesn't imply monetary value. The word "payoff" seems to suggest that you are thinking of money. Even throwing dice or choosing playing cards need have no monetary implication. Jul 13, 2016 at 18:57 • Expected value relates to the expectation of some random variable (a formally-defined random variable is always numeric, but not necessarily monetary). Jul 13, 2016 at 23:47 • @Glen_b could you check my example 2? Am I right the expectation does not have any physical meaning such case? Jul 14, 2016 at 14:46 • @hxd1011 this is already addressed in my previous comment. Your$Y$does not formally meet the requirements of a random variable in the standard sense. For example see the distinction drawn here and here between a random variable and a random element. Sometimes people may call such a variable a random variable but the most common definition would require us to map outcomes to elements of$\mathbb{R}$to get a random variable. Jul 14, 2016 at 18:07 ## 3 Answers There are several words that can have different meanings in statistics and other fields or every day life in your question. For instance fair in the context of throwing a die means that all sides have the same probability of occurring. The same word has a different meaning in game theory, where fair price means a price you'd pay for a lottery which eliminates the profit from the payoffs. The word expected in statistics means this: $$E[x]=\sum_{i=1}^6p_ix_i=\frac{1}{6}\1+\frac{1}{6}\2+\dots+\frac{1}{6}\6$$ where$i\in{1,2,3,4,5,6}$- an index of the side,$p_i$the probability to get this side, and$x_i$- the outcome of a trial (payoff). If the payoff was in dollars and the die is fair you could easily see how this is equal to$3.5.

The outcome (payoff) that happens most often is called a mode. In the case of a fair die, all outcomes are equally probable, so the mode is not an interesting measure.

UPDATE: So, if you think of a fair dice as a tool which generates payoff randomly depending on which side was tossed, then yes, $3.5 is a fair price you'd pay for this tool assuming there's no time value of money. There are complications, into which you can dig in if interested, things like ST. Petersburg paradox etc. UPDATE 2: @hxd1011 asked whether there's a physical meaning to that referring to his Example 2 with the possible outcome to be animals. Right, the expected value is of the values of a random variable. The random variables in statistics are defined as some - usually real - values that are linked to events from the event space. Do not mix them with indices. For instance, in your example 2 let's denote the events with indices$j={1,2,3}$, then we can enumerate all possible events:$\omega_1=\text{cat},\omega_2=\text{dog},\omega_3=\text{pig}$. Let's say we have the associated probabilities$p_1=p_2=p_3=1/3$. If you did not define the random variable$x_i$yet, then there's no point in talking about the expected value at all. Expected value of what? Of index$j$? It doesn't have any physical meaning as you wrote. Let's now define a random variable$xon the probability space as follows (suppose we have some hypothetical game that if you guess correctly you will get some money): \begin{align} x&=\10,\quad\text{if }\omega=\text{cat} \\ x&=\$20,\quad\text{if }\omega=\text{dog} \\ x&=\$30,\quad\text{if }\omega=\text{pig} \end{align} Now we can talk about the expected value of $E[x]$. We can calculate it easily using the equation above, it's $\$20$of course. • could you check my example 2? does the expectation have some physical meaning for that? Jul 14, 2016 at 14:45 • @hxd1011, I updated my answer. sorry for confusion Jul 14, 2016 at 17:28 • +1 for really nice answer that point out "random variables are defined as some real values that are linked to events from the event space." Jul 14, 2016 at 17:36 The expected value corresponds to the value you should expect to obtain, on average, if you repeat the action MANY times. In your example of the fair dice, if you assume that all sides are equally likely (probability 1/6 each) and if you were to do try many times, on average you would get the value: 1 * 1/6 + 2 * 1/6 + 3 * 1/6 4 * 1/6 + 5* 1/6 + 6 * 1/6 = 3.5 But, if the dice was not fair (assume for example that it never gives you a 1, but the 6 is twice as likely as usual), then the expected value would be: 1 * 0 + 2 * 1/6 + 3 * 1/6 4 * 1/6 + 5* 1/6 + 6 * 2/6 = 4.3 Note that the expected value does not need to correspond with any actual (integer) value you can obtain in one particular realization. Your confusion is coming from the definition of discrete random variables. I will use two examples to illustrate. Example 1. Assume you can receive$X$mails a day,$X$is a discrete number that can be$0,1,2,\cdots$. Assume you collected 1 week data, and it is$(1,2,3,4,5,6,7)$. So, the expected value / average is$4$. So you know the physical meaning is on average you will receive$4$mails a day. This is the case that the expected value has intuitive physical meaning. Example 2. Assume there is an animal in the room, but you do not if it is a cat or dog or pig. Let's use$\Omega \in \{\text{cat,dog,pig}\}$to represent the possible outcome. Note, As @Glen_b, @whuber, and @Aksakal mentioned, we cannot think$\Omega$is a random variable, because iti s not a real number. So, we need to use some mapping to build random variables. Let us use$Y \in \{1,2,3\}$to be a discrete random variable and represent$\{\text{cat,dog,pig}\}$, and you collect$7$data points, they are$(1,1,1,1,1,1,2)$so the expected value is$1.142$. Here is where your confusion comes from: what does this number mean? This number does not have physical meaning, i.e., which animal it is. To conclude, you confusion comes from the definition of discrete random variable and the expectation. The expectation does always have concrete physical meaning. • There appears to be a confusion here between an outcome and a random variable. In your example, despite the suggestive notation,$Y\$ is an outcome, not a random variable.
– whuber
Jul 14, 2016 at 18:46
• @whuber thanks for the comment, you are wright some of my concept is not clear. I also learned form Glen_b, that difference between random variable and random elements. Jul 14, 2016 at 19:07
• If you are interested, I attempted to address these issues in a non-mathematical but rigorous way in the thread on what is meant by a random variable.
– whuber
Jul 14, 2016 at 19:31


text:
Cuffdiff De Significance Of Zero Fpkm Values
1
1
Entering edit mode
10.2 years ago
Jason ▴ 10

Hi-

I was using cuffdiff 1.3.0 to compare four BAMs aligned with TopHat 1.4.1. I have noticed that zero FPKM values are never considered significant when compared with large FPKM values. Here is one example that I am concerned about:

XLOC_017834    XLOC_017834    Olfr1307    2:111784672-111785611    FF    FMC    OK    0.257545    46.5301    7.4972    -4.50075    6.77156e-06    0.000658507    yes
XLOC_017834    XLOC_017834    Olfr1307    2:111784672-111785611    FFC    FMC    OK    0    46.5301    1.79769e+308    1.79769e+308    0.0789649    0.365761    no
XLOC_017834    XLOC_017834    Olfr1307    2:111784672-111785611    FM    FMC    OK    0.0380371    46.5301    10.2565    -5.37179    7.79602e-08    2.39776e-05    yes

If line wrapping destroys the above genesexp.diff output, here is a brief summary: FMC has an FPKM of 46.5301 and when compared to FF (FPKM=0.257545) and FM (FPKM=0.0380371) the q-value is below the FDR of 0.05. Appropriately the significance value is labeled as 'yes'. However, FFC has an FPKM of zero and this differential test is not significant. The goal of the experiment was to identify uniquely expressed genes only identified in the FMC data set. As such an infinite log(foldchange) seems more significant than the other comparisons. Can anyone explain this?

cufflinks cuffdiff fpkm rna-seq • 5.5k views
0
Entering edit mode

HI Jason,

Did you find a way to deal with this problem. I am running into the same problem: A lot of genes in my cuffdiff output that have 0 FPKM in one condition and very high FPKM values in the other condition.

Thank you
Linda

0
Entering edit mode

Hi Jason and Molla Linda,

I am facing the same issue. How did you handle it?

2
Entering edit mode
10.2 years ago
seidel 9.5k

How does one measure the significance of something that wasn't measured? I think what you're asking for is the authors of cuffdiff to make up a heuristic, whereby if something is measured with significance in one sample (high FPKM), but not measured at all in another, they should invent a significance value and flag that gene as significantly differentially expressed - a ratio of infinity, is after all, pretty significant. The difficulty is that there's an absence of data for one side of the comparison, thus one can't effectively assign any numerical significance to that particular comparison. To do so, would be making something up (the friendlier term is: creating a heuristic). Getting people to agree on a heuristic or a convention for this situation may be difficult.

If you are looking for genes that meet this criteria, there's no reason why you can't make up your own heuristic for identifying them and pulling them out of the cuffdiff results. Even then, you'll have to make some decision about what FPKM value in a given set of samples would be significantly different from 0 in another.


text:
# How to move equation numbers to right hand side?

I'm writing a mathematical article and I want the equation numbers to appear on the right hand side and the end of the line however they are currently appearing underneath the equation on the left. How can I change this?

EXAMPLE:

\documentclass{article}
\usepackage[utf8]{inputenc}

\usepackage{natbib}
\usepackage[section]{placeins}
\usepackage{graphicx}
\usepackage{wrapfig}
\usepackage{float}
\usepackage{mathtools}
\usepackage{amsmath}
\usepackage{geometry}
\geometry{ a4paper, total={170mm,257mm}, left=20mm, top=20mm, }

\begin{document}
\maketitle

\section{Equations}
The horizontal and vertical links and network nodes can now be defined as the following matrices: \

For 1 \leq i \leq m+1 \ $and$ \ 1 \leq j \leq n

\begin{description}
\item[(a)]

$$A_{ij}^X= \begin{cases} 1, & \text{if the link between (i,j) and (i,j+1) exists}\ \ 0, & \text{otherwise}\ \ \end{cases}$$

\item[(b)]

$$X_{ij} = l_{ij}$$

where $l_{ij}$ is the length of the link between ($i,j$) and ($i,j+1$). If >there is no link between ($i,j$) and ($i,j+1$) then $l_{ij}$=0

\end{description}

\bibliographystyle{plain}
\bibliography{references}
\end{document}

• Welcome to TeX.SX! Right hand side is the default, so you have leqno or some different setup apparently? – user31729 Nov 16 '15 at 17:41
• Which document class do you use? – Mico Nov 16 '15 at 17:42
• I'm using article at the moment – MCCR Nov 16 '15 at 17:43
• Do you use at one-column or a two-column layout? – Mico Nov 16 '15 at 17:44
• A one-column layout – MCCR Nov 16 '15 at 17:44

Your coding style is, shall we way, not exactly tidy. Here's a minimalist fix-up that should get you going, at least for a little while. Good news: after the code clean-up, the equation numbers show up on the right-hand edge.

\documentclass{article}

\usepackage[utf8]{inputenc}
\usepackage{natbib}
\usepackage[section]{placeins}
\usepackage{graphicx}
\usepackage{wrapfig}
\usepackage{float}
\usepackage{mathtools}
%%\usepackage{amsmath}  is loaded by 'mathtools' -- no need to load it explicitly
\usepackage{geometry}
\geometry{ a4paper, total={170mm,257mm}, left=20mm, top=20mm}

\begin{document}

\section{Equations}

The horizontal and vertical links and network nodes can now be defined as the following matrices

For $1 \leq i \leq m+1$ and $1 \leq j \leq n$

\begin{description}
\item[(a)]
$$A_{ij}^X= \begin{cases} 1, & \text{if the link between (i,j) and (i,j+1) exists}\\ 0, & \text{otherwise} \end{cases}$$

\item[(b)]
$$X_{ij} = l_{ij}$$
where $l_{ij}$ is the length of the link between ($i,j$) and ($i,j+1$).
If there is no link between ($i,j$) and ($i,j+1$) then $l_{ij}$=0

\end{description}
\end{document}

• Thanks yeah that's changed it :) yeah I have just been googling as I go along... – MCCR Nov 16 '15 at 18:16


text:
# Beam Echo Measurements at CERN

#### The last few hours of SPS running in 1995, devoted to machine studies, delivered the first longitudinal echo signals in a coasting proton beam stored at 120 GeV (CERN Bullettin, January 1996). Echo phenomena have been well known in plasma physics for many years. However the effect has only been observed recently in accelerators. The first measurements were made at the beginning of 1995 in the 8 GeV anti-proton accumulator at Fermilab, but it was not clear whether the effect would be observable in a big machine like the SPS. The implications could be promising, both for the SPS and for the LHC. Potential applications of this new technique are the fast detection of weak longitudinal diffusion, beam energy spread measurements and possibly impedance measurements.

An echo is formed by the interference of two consecutive RF pulses with slightly different frequencies. Each RF excitation induces a well defined pattern of particle energy along the machine circumference, rapidly destroyed by the revolution frequency spread. However, the long lasting memory of the proton beam allows the reappearence of an ordered structure long after the initial excitations. The timing of the echo response depends on the frequency of the kicks and their separation; the longer the separation, the later the echo: in the SPS we have observed echo delays up to two minutes (corresponding to more than 5 millions turns). The left-top picture shows the super-imposition of 22 echo measurements with different time separations between the two RF-kicks, ranging from 5 to 220 ms. The vertical axis shows the absolute value of the echo amplitude on a linear scale and the horizontal axis shows the time measured from the first RF-kick. The horizontal scale is 50 s. The solid line shows the analytical estimate for the echo envelope assuming a diffusion coefficient of $10-13$ s$-1$: in order to observe such a small diffusion with the Schottky signal, one would have to wait more than one day.

Following the links in this page you can get full information about analytic calculations, numeric simulations and echo measurements performed at CERN, including measurements in LEAR and bunched beam echoes recently observed in the SPS.

Background bibliography:
• T.M. O' Neil and R.W. Gould, Phys. Fluids 11, 1 (1968).
• E.M. Lifshitz and L.P. Pitaivskii, Physical Kinetics, Pergamon Press, Oxford, 1981.
• G.V. Stupakov, Echo Effect In Hadron Colliders, SSC Report SSCL-579, July 1992.
• G.V. Stupakov and S. Kauffmann, Echo Effect in Accelerators, SSC Report SSCL-587, September 1992.
• P.L. Colestock, L.K. Spenzouris and J.-F. Ostiguy, Nonlinear Wave Phenomena in Coasting Beams, Proc. IEEE Particle Accelerator Conference, Dallas, 1995, pp. 2757-2761.
• L.K. Spenzouris, J.-F. Ostigy, P.L. Colestock, Direct measurement of diffusion rates in high energy synchrotrons using longitudinal beam echoes, Phys. Rev. Letters 76, 620 (1996).

21/05/1997 Francesco.Ruggiero@cern.ch


text:
# Quantum Mechanics: Raising and Lowering Operators

1. Apr 25, 2015

### Robben

1. The problem statement, all variables and given/known data

Consider a particle in an energy eigenstate $|n\rangle.$

Calculate $\langle x\rangle$ and $\langle p_x\rangle$ for this state.

2. Relevant equations

$x = \sqrt{\frac{\hbar}{2m\omega}}(a+a^{\dagger})$

3. The attempt at a solution

$\langle x\rangle = \sqrt{\frac{\hbar}{2m\omega}}\langle n(a + a^{\dagger})|n\rangle = \sqrt{\frac{\hbar}{2m\omega}}(\sqrt{n}\langle n|n-1\rangle+\sqrt{n+1}\langle n|n+1\rangle).$

But why does it equal zero?

2. Apr 25, 2015

### ShayanJ

The energy eigenstates form an orthonormal set and here is no different. So $\langle n|m\rangle=\delta_{nm}$.

3. Apr 25, 2015

### Robben

So, $\langle n|n+1\rangle = 0$ and $\langle n|n-1\rangle$ equal zero from the property of the dirac function?

4. Apr 25, 2015

### ShayanJ

Yes!

5. Apr 25, 2015

### ShayanJ

And that is Kronecker delta, not Dirac delta!

6. Apr 26, 2015

### Robben

Opps! Thanks for clarifying.


text:
## Valence Applies for $225M in DOE Funds for Advanced Battery Production Facility ##### 28 May 2009 Valence Technology, Inc. submitted a grant application requesting$225 million to the US Department of Energy under the Electric Drive Vehicle Battery and Component Manufacturing Initiative.

This initiative supports the construction of facilities to manufacture advanced battery technology components for electric vehicles. The company’s proposed facility in Leander, Texas would manufacture lithium phosphate cathode material, high-capacity advanced cells and battery packs for electric drive vehicles and other applications.

Valence submitted its application requesting the federal grant funds over a three-year period and plans to fund the remaining \$359.4 million (61.5% of the total project costs) through Texas state and local tax and other incentives. The annual production capacity of the proposed facility is estimated to be 660,000 battery packs or more than one million kilowatt hours (kWh) of equivalent available energy and can be online as early as August 2012.

This grant application is a separate request from the Valence’s March loan application under the Advanced Technology Vehicles Manufacturing Incentive Program (ATVMIP) for low interest loans to help finance the construction of this new lithium iron magnesium phosphate battery manufacturing facility. Funds under both programs are available to qualified companies.


text:
### E-20.001 - Act respecting the exercise of certain municipal powers in certain urban agglomerations

59. The order must respect the following principles:
(1)  every related municipality must be represented on the urban agglomeration council;
(2)  the number of votes assigned to the representative or to all the representatives of each related municipality must be in the same proportion to the number of votes assigned to all the members of the urban agglomeration council as the population of the municipality is to the total population of all the related municipalities; and
(3)  the meetings of the urban agglomeration council must be public.
2004, c. 29, s. 59.


text:
Public Group

# Vectors of Classes

This topic is 4175 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

## Recommended Posts

I want to create a vector of the class that I am working with. I can currently successfully create an array with the class, but I am having troubles with the vector class. Here is the code that I have so far:

#include <string>
#include <vector>
#include <iostream>

using namespace std;

//////////////////////////////////////////////////////////////////
// R E F E R E N C E  C L A S S                             ****//
//////////////////////////////////////////////////////////////////

class Reference                                                 // Parent
{
private:
//declare all variables
string Author, Title, Journal, Year, Volume, Number, Pages, Note;
string Key, Booktitle, Editor, Organisation, Publisher, Address, Month;
string Series, Edition, Institution, Type, Howpublished;
string ReferenceType;
public:
Reference(string refType)
{
ReferenceType = refType;
}

//set functions
void setAuthor(string author);
void setTitle(string title);
void setJournal(string journal);
void setYear(string year);
void setVolume(string volume);
void setNumber(string number);
void setPages(string pages);
void setNote(string note);
void setKey(string key);
void setBooktitle(string booktitle);
void setEditor(string editor);
void setOrganisation(string organisation);
void setPublisher(string publisher);
void setMonth(string month);
void setSeries(string series);
void setEdition(string edition);
void setInstitution(string institution);
void setType(string type);
void setHowpublished(string howpublished);

//get functions
string getAuthor();
string getTitle();
string getJournal();
string getYear();
string getVolume();
string getNumber();
string getPages();
string getNote();
string getKey();
string getBooktitle();
string getEditor();
string getOrganisation();
string getPublisher();
string getMonth();
string getSeries();
string getEdition();
string getInstitution();
string getType();
string getHowpublished();

string ReturnReference();

};

//set functions
void Reference::setAuthor(string author) {Author = author;}
void Reference::setTitle(string title) {Title = title;}
void Reference::setJournal(string journal) {Journal = journal;}
void Reference::setYear(string year) {Year = year;}
void Reference::setVolume(string volume) {Volume = volume;}
void Reference::setNumber(string number) {Number = number;}
void Reference::setPages(string pages) {Pages = pages;}
void Reference::setNote(string note) {Note = note;}
void Reference::setKey(string key) {Key = key;}
void Reference::setBooktitle(string booktitle) {Booktitle = booktitle;}
void Reference::setEditor(string editor) {Editor = editor;}
void Reference::setOrganisation(string organisation) {Organisation = organisation;}
void Reference::setPublisher(string publisher) {Publisher = publisher;}
void Reference::setMonth(string month) {Month = month;}
void Reference::setSeries(string series) {Series = series;}
void Reference::setEdition(string edition) {Edition = edition;}
void Reference::setInstitution(string institution) {Institution = institution;}
void Reference::setType(string type) {Type = type;}
void Reference::setHowpublished(string howpublished) {Howpublished = howpublished;}

//get funcitons
string Reference::getAuthor() {return Author;}
string Reference::getTitle() {return Title;}
string Reference::getJournal() {return Journal;}
string Reference::getYear() {return Year;}
string Reference::getVolume() {return Volume;}
string Reference::getNumber() {return Number;}
string Reference::getPages() {return Pages;}
string Reference::getNote() {return Note;}
string Reference::getKey() {return Key;}
string Reference::getBooktitle() {return Booktitle;}
string Reference::getEditor() {return Editor;}
string Reference::getOrganisation() {return Organisation;}
string Reference::getPublisher() {return Publisher;}
string Reference::getMonth() {return Month;}
string Reference::getSeries() {return Series;}
string Reference::getEdition() {return Edition;}
string Reference::getInstitution() {return Institution;}
string Reference::getType() {return Type;}
string Reference::getHowpublished() {return Howpublished;}

string Reference::ReturnReference()
{
if (ReferenceType == "Book")
{
//output book reference
string tempRef;
string tempYear;
string tempEd;
string tempVol;
string tempEdVol="";
string tempPub;

if (Year != "") //if the year exists, include it
{
tempYear = "(" + Year + ").";
}

if (Edition != "") //check if edition exists
{
tempEd = Edition + " ed.";
}

if (Volume != "") //check if volume exists
{
tempVol = "Vol " + Volume + ".";
}

if ((Volume != "") && (Edition != "")) //if they both exist
{
tempEdVol = "(" + tempEd + " " + tempVol + ").";
}

if ((Volume ==  "") && (Edition != "")) //just edition exists
{
tempEdVol = "(" + tempEd + ").";
}

if ((Volume != "") && (Edition == "")) //just volume exists
{
tempEdVol = "(" + tempVol + ").";
}

if (Publisher != "") {tempPub = ":" + Publisher;}

tempRef = Author + " " + tempYear + " " + Title + " " + tempEdVol + " " + Address + tempPub;

return tempRef;
}

}

int main()
{

//Reference aBook("Book");

//aBook.setAuthor("Daniel Beard");
//aBook.setTitle("This is the title");
//aBook.setYear("1999");
//aBook.setEdition("Fifth");
//aBook.setVolume("3");
//aBook.setPublisher("Cheese Publishing");

vector<Reference> ref;
int i;
i = 1;

ref.push_back("Book");
ref.setAuthor("Daniel");
ref.setTitle("This is a title");
ref.setYear("1999");

//cout << aBook.ReturnReference() << endl;
cout << ref.ReturnReference() << endl;

}

The commented out code is the code that works, however, I would prefer to be using vectors rather than arrays, so I tried to create new vectors of the class. The above code gives a compile error : /Users/dan/Desktop/New Reference Class/main.cp:194: error: no matching function for call to 'std::vector<Reference, std::allocator<Reference> >::push_back(const char [5])' How would I call a new vector of the Reference class? Thanks, Dan

##### Share on other sites
ref.push_back(Reference("Book"));

You are attempting to add a C-style string onto a vector of Reference objects, which won't work. First you need to construct a Reference object from the string. Also, you'll run into problems if you don't have a copy constructor and assignment operator:

Reference (const Reference &ref){    //Copy ref's class variables    ...}Reference &operator= (const Reference &ref){    //Set class variables    ...    return *this;}

##### Share on other sites
strtok already answered the biggest issue with what you're asking, but also wanted to add a quick note. Vector element indexing starts with 0, like arrays, so you'll want to be careful with that. Above, the first push_back would put the first object at element[0], so an attempt to access members at element[1] wouldn't work until a second push_back occured.

Scorp

##### Share on other sites
Why do I need to copy the ref class variables?
There is only one class, the Reference class, and what does the operator function do?
I don't really understand what I have to put in those two functions that you suggested to add.

Thanks
Dan

##### Share on other sites
I would be best leaving the copy method for someone else to explain correctly, but as far as the assignment operator function, I'll take a stab at that one.

If you have two different int variables, foo and bar, it's easy to simply code "foo = bar;". That's because the data type implementation has the necessary code already there to take the value of bar and store it into foo.

With a custom data type, the Reference class in this case, that code doesn't exist, because it's your own data type. By adding that class method, it gives you the same type of functionality as described with the int variables, only with your class objects instead.

If you're wondering where it might be useful, anytime you have the need to simply say "Reference A = Reference B", your class knows how to make that happen, by assigning all of the class members the correct values. Otherwise, if you try to do that with a custom data type, your compiler is going to complain, saying that it cannot find any operator function.

Hope that makes some sense :)
Scorp

##### Share on other sites
I changed the line to ref.push_back(Reference("Book"));
Now I am getting the error:

New Reference Class has exited due to signal 11 (SIGSEGV).

Can anyone help me, I don't know what to put in the copy constructor or the operator overloading.

Thanks
Dan

##### Share on other sites
Did you change the int i to 0 instead of 1? I mentioned earlier about vectors being 0-based, which one needs to be careful of. I'm only asking that because the code as it is, with that exception and
ref.push_back(Reference("Book"));

it compiles and runs fine for me.

As far as what will go in the other two functions, I honestly don't know if I would worry about that a ton at this time, because your class doesn't have any members that require dynamic memory allocation. With that, the defaults it will run with may work ok. If not, then tackle those. But for now, try changing how you're indexing the vector array and see what happens.

{Edit} I said it compiles fine and runs, which it does, but with one warning. That warning points out that in your ReturnReference method, it doesn't return a value (object) on all return paths. For example, if the reference object type is not "Book", nothing is returned, which could cause the calling code to crash.
{/Edit}

Cheers!
Scorp

##### Share on other sites
Quote:
 Original post by paintstripper88I changed the line to ref.push_back(Reference("Book"));Now I am getting the error:New Reference Class has exited due to signal 11 (SIGSEGV).

Maybe what Scorp07, noticed, inserting a Reference at index 0 and accessing a nonexistent one at index 1?
Can't you fill the data before inserting into the vector? It would be simpler and more efficient.

##### Share on other sites
0) The vector is a vector of References, so you can't push_back a std::string into it; you have to push_back a Reference into it. That means constructing a Reference first, and then putting it in. strtok's example does that by constructing an anonymous Reference; you don't need a variable of Reference type in order to make it work. This is the same as when you have a function "void foo(int)", and you call it with "foo(42);", instead of "int value = 42; foo(value);".

1) Clearly you didn't successfully work with an array of the class instances, because (a) your "working" commented-out code does nothing of the sort - it simply works with a single instance; and (b) the problem with the vector is one that you'd have with an array as well: array indices start at 0, not 1. This is done because it makes your life easier in the long run. Specifically, whenever you need to calculate an array index, you will find that the 0-based indexing leads to simpler math, with fewer strange +1's and -1's needed to make things line up right.

std::vector copies the array "interface" in this regard because (a) it is expected (by experienced programmers), (b) it was easier (for the implementor), and (c) it is easier (again, for experienced programmers to work with, for the same reasons it is with the array).

2) However, it makes more sense to construct the object fully before putting it in, instead of "reaching in" to the vector to set the other values.

3) Whatever book told you to write all those set and get functions - burn it. It is lying to you about what "encapsulation" means in C++, and making you do extra work - on both sides of the class - for something that actually isn't any better encapsulated at all. With the existing definition of the class, the only thing we should be hiding is the "ReferenceType" - because that value should never change or be inspected from outside after construction.

4) However, that's still awful design. Evidently, not all of the provided fields make sense for all the different "types" of references. In C++, we don't indicate sub-types by setting a field and checking it later; we indicate them by actually creating subtypes. Then, the parent Reference type only needs to contain those fields that are needed by all different sorts of References.

I didn't try to make the corresponding changes, though, because I don't know what kinds of References you need, and what data is appropriate for each.

5) In C++, we don't convert objects into strings for printing. Instead, we define how to feed them to output streams. Then, we can feed them directly (just like we do with ints or std::string instances) instead of calling the string-conversion function.

6) As noted, functions need to return something in all cases. The old ReturnReference() function had this problem: if the Reference *isn't* a book, what gets returned? The answer, according to C++ is, "I dunno, lol". The compiled code will blindly pick up whatever memory was in the chunk where it was expecting the return value to be, and pretend that garbage data represents a std::string object. All hell breaks loose after that. If you're lucky, the program will just crash right away. If not, you might get garbage output, or even something that seems to work fine, and then at some seemingingly random later time, your program crashes in a *completely different* place where the surrounding code is actually perfectly OK on its own. This is what we call "undefined behaviour".

7) Also in C++, we use initialization lists in constructors, as shown, and normally pass arguments of complex types (such as std::string) by const reference, as shown.

8) Oh, and don't waste time making fancy box comments. You'll regret it when you realize you need to change the comment for some reason, and waste more time keeping it "pretty". For that matter, don't waste time making a "the Foo class is here" type comment. You're not making it any easier to search for the Foo class in your code; just use 'class Foo' for your search text.

9) Don't compare strings to empty strings; use .empty() instead. It's clearer about what you mean ("is the string empty?").

10) And some other stuff, but it's easier to just show than explain...

#include <string>#include <vector>#include <iostream>using namespace std;class Reference {	string ReferenceType;	public:	string Author, Title, Journal, Year, Volume, Number, Pages, Note;	string Key, Booktitle, Editor, Organisation, Publisher, Address, Month;	string Series, Edition, Institution, Type, Howpublished;	Reference(const string& ReferenceType) : ReferenceType(ReferenceType) {}		friend ostream& operator<<(ostream&, const Reference&);}; ostream& operator<<(ostream& os, const Reference& r) {	if (r.ReferenceType == "Book") {		// Output each of the following in order, if they exist:		// author, year, title, edition/volume, address, publisher.		os << r.Author << " ";		if (!r.Year.empty()) { os << "(" << r.Year << ")."; }		os << " " << r.Title << " ";		bool haveEdition = !r.Edition.empty();		bool haveVolume = !r.Volume.empty();		if (haveEdition || haveVolume) {			// Pay close attention to the logic here ;)			os << "(";			if (haveEdition) { os << r.Edition << " ed."; }			if (haveEdition && haveVolume) { os << " "; }			if (haveVolume) { os << "Vol " << r.Volume << "."; }			os << ").";		}		os << " " << r.Address;		if (!r.Publisher.empty()) {			os << ":" << r.Publisher;		}	}	// We do this part even if it wasn't a Book:	return os;	// The result, if it's not a Book, is that nothing is printed, but the	// program carries on without any problems.}int main() {	vector<Reference> ref;	int i = 0; // Don't declare variables and then assign to them right	// away; instead, really *initialize* them. Also note the value ;)		Reference r("Book");	r.Author = "Daniel";	r.Title = "This is a title";	r.Year = "1999";		// Test it as is:	cout << r << endl;	// Test it within the vector:	ref.push_back(r);	cout << ref << endl; // see how easy :)}

1. 1
Rutin
44
2. 2
3. 3
4. 4
5. 5

• 11
• 9
• 12
• 10
• 13
• ### Forum Statistics

• Total Topics
632983
• Total Posts
3009708
• ### Who's Online (See full list)

There are no registered users currently online

×